Major Graphic Engine revision. Now most of the math functions are broken
due to their outdated rendering methods.
This commit is contained in:
parent
de0340b166
commit
bbdba7aeb3
@ -3,6 +3,7 @@
|
|||||||
<classpathentry excluding="org/warp/picalculator/deprecatedmath/" kind="src" path="src"/>
|
<classpathentry excluding="org/warp/picalculator/deprecatedmath/" kind="src" path="src"/>
|
||||||
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
|
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/>
|
||||||
<classpathentry kind="src" path="res"/>
|
<classpathentry kind="src" path="res"/>
|
||||||
|
<classpathentry exported="true" kind="con" path="org.eclipse.jdt.USER_LIBRARY/JOGL"/>
|
||||||
<classpathentry kind="lib" path="libs/pi4j-1.1/pi4j-core.jar" sourcepath="libs/pi4j-1.1/pi4j-core-sources.jar">
|
<classpathentry kind="lib" path="libs/pi4j-1.1/pi4j-core.jar" sourcepath="libs/pi4j-1.1/pi4j-core-sources.jar">
|
||||||
<attributes>
|
<attributes>
|
||||||
<attribute name="javadoc_location" value="jar:platform:/resource/PICalculator/libs/pi4j-1.1/pi4j-core-javadoc.jar!/"/>
|
<attribute name="javadoc_location" value="jar:platform:/resource/PICalculator/libs/pi4j-1.1/pi4j-core-javadoc.jar!/"/>
|
||||||
@ -28,6 +29,5 @@
|
|||||||
<attribute name="javadoc_location" value="jar:platform:/resource/PICalculator/libs/objenesis-2.4/objenesis-2.4-javadoc.jar!/"/>
|
<attribute name="javadoc_location" value="jar:platform:/resource/PICalculator/libs/objenesis-2.4/objenesis-2.4-javadoc.jar!/"/>
|
||||||
</attributes>
|
</attributes>
|
||||||
</classpathentry>
|
</classpathentry>
|
||||||
<classpathentry kind="con" path="org.eclipse.jdt.USER_LIBRARY/JOGL"/>
|
|
||||||
<classpathentry kind="output" path="bin"/>
|
<classpathentry kind="output" path="bin"/>
|
||||||
</classpath>
|
</classpath>
|
||||||
|
@ -1,12 +1,2 @@
|
|||||||
eclipse.preferences.version=1
|
eclipse.preferences.version=1
|
||||||
org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
|
org.eclipse.jdt.core.javaFormatter=org.eclipse.jdt.core.defaultJavaFormatter
|
||||||
org.eclipse.jdt.core.compiler.codegen.methodParameters=do not generate
|
|
||||||
org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8
|
|
||||||
org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
|
|
||||||
org.eclipse.jdt.core.compiler.compliance=1.8
|
|
||||||
org.eclipse.jdt.core.compiler.debug.lineNumber=generate
|
|
||||||
org.eclipse.jdt.core.compiler.debug.localVariable=generate
|
|
||||||
org.eclipse.jdt.core.compiler.debug.sourceFile=generate
|
|
||||||
org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
|
|
||||||
org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
|
|
||||||
org.eclipse.jdt.core.compiler.source=1.8
|
|
||||||
|
60
.settings/org.eclipse.jdt.ui.prefs
Normal file
60
.settings/org.eclipse.jdt.ui.prefs
Normal file
@ -0,0 +1,60 @@
|
|||||||
|
cleanup.add_default_serial_version_id=false
|
||||||
|
cleanup.add_generated_serial_version_id=true
|
||||||
|
cleanup.add_missing_annotations=true
|
||||||
|
cleanup.add_missing_deprecated_annotations=true
|
||||||
|
cleanup.add_missing_methods=true
|
||||||
|
cleanup.add_missing_nls_tags=false
|
||||||
|
cleanup.add_missing_override_annotations=true
|
||||||
|
cleanup.add_missing_override_annotations_interface_methods=true
|
||||||
|
cleanup.add_serial_version_id=true
|
||||||
|
cleanup.always_use_blocks=true
|
||||||
|
cleanup.always_use_parentheses_in_expressions=true
|
||||||
|
cleanup.always_use_this_for_non_static_field_access=false
|
||||||
|
cleanup.always_use_this_for_non_static_method_access=false
|
||||||
|
cleanup.convert_functional_interfaces=true
|
||||||
|
cleanup.convert_to_enhanced_for_loop=true
|
||||||
|
cleanup.correct_indentation=true
|
||||||
|
cleanup.format_source_code=true
|
||||||
|
cleanup.format_source_code_changes_only=false
|
||||||
|
cleanup.insert_inferred_type_arguments=false
|
||||||
|
cleanup.make_local_variable_final=true
|
||||||
|
cleanup.make_parameters_final=false
|
||||||
|
cleanup.make_private_fields_final=true
|
||||||
|
cleanup.make_type_abstract_if_missing_method=false
|
||||||
|
cleanup.make_variable_declarations_final=true
|
||||||
|
cleanup.never_use_blocks=false
|
||||||
|
cleanup.never_use_parentheses_in_expressions=false
|
||||||
|
cleanup.organize_imports=false
|
||||||
|
cleanup.qualify_static_field_accesses_with_declaring_class=false
|
||||||
|
cleanup.qualify_static_member_accesses_through_instances_with_declaring_class=true
|
||||||
|
cleanup.qualify_static_member_accesses_through_subtypes_with_declaring_class=true
|
||||||
|
cleanup.qualify_static_member_accesses_with_declaring_class=true
|
||||||
|
cleanup.qualify_static_method_accesses_with_declaring_class=false
|
||||||
|
cleanup.remove_private_constructors=true
|
||||||
|
cleanup.remove_redundant_type_arguments=true
|
||||||
|
cleanup.remove_trailing_whitespaces=false
|
||||||
|
cleanup.remove_trailing_whitespaces_all=true
|
||||||
|
cleanup.remove_trailing_whitespaces_ignore_empty=false
|
||||||
|
cleanup.remove_unnecessary_casts=true
|
||||||
|
cleanup.remove_unnecessary_nls_tags=true
|
||||||
|
cleanup.remove_unused_imports=true
|
||||||
|
cleanup.remove_unused_local_variables=false
|
||||||
|
cleanup.remove_unused_private_fields=true
|
||||||
|
cleanup.remove_unused_private_members=false
|
||||||
|
cleanup.remove_unused_private_methods=true
|
||||||
|
cleanup.remove_unused_private_types=true
|
||||||
|
cleanup.sort_members=false
|
||||||
|
cleanup.sort_members_all=false
|
||||||
|
cleanup.use_anonymous_class_creation=false
|
||||||
|
cleanup.use_blocks=true
|
||||||
|
cleanup.use_blocks_only_for_return_and_throw=false
|
||||||
|
cleanup.use_lambda=true
|
||||||
|
cleanup.use_parentheses_in_expressions=false
|
||||||
|
cleanup.use_this_for_non_static_field_access=true
|
||||||
|
cleanup.use_this_for_non_static_field_access_only_if_necessary=true
|
||||||
|
cleanup.use_this_for_non_static_method_access=true
|
||||||
|
cleanup.use_this_for_non_static_method_access_only_if_necessary=true
|
||||||
|
cleanup_profile=_Drake's Cleanup
|
||||||
|
cleanup_settings_version=2
|
||||||
|
eclipse.preferences.version=1
|
||||||
|
formatter_settings_version=12
|
BIN
res/skin.png
BIN
res/skin.png
Binary file not shown.
Before Width: | Height: | Size: 4.7 KiB After Width: | Height: | Size: 4.5 KiB |
BIN
res/skin.xcf
BIN
res/skin.xcf
Binary file not shown.
BIN
res/test.png
Normal file
BIN
res/test.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 1.1 KiB |
@ -64,7 +64,7 @@ public class Cloner {
|
|||||||
private boolean cloneSynthetics = true;
|
private boolean cloneSynthetics = true;
|
||||||
|
|
||||||
public Cloner() {
|
public Cloner() {
|
||||||
this.instantiationStrategy = ObjenesisInstantiationStrategy.getInstance();
|
instantiationStrategy = ObjenesisInstantiationStrategy.getInstance();
|
||||||
init();
|
init();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -113,12 +113,12 @@ public class Cloner {
|
|||||||
fastCloners.put(ConcurrentHashMap.class, new FastClonerConcurrentHashMap());
|
fastCloners.put(ConcurrentHashMap.class, new FastClonerConcurrentHashMap());
|
||||||
}
|
}
|
||||||
|
|
||||||
private IDeepCloner deepCloner = new IDeepCloner() {
|
private final IDeepCloner deepCloner = new IDeepCloner() {
|
||||||
@Override
|
@Override
|
||||||
public <T> T deepClone(T o, Map<Object, Object> clones) {
|
public <T> T deepClone(T o, Map<Object, Object> clones) {
|
||||||
try {
|
try {
|
||||||
return cloneInternal(o, clones);
|
return cloneInternal(o, clones);
|
||||||
} catch (IllegalAccessException e) {
|
} catch (final IllegalAccessException e) {
|
||||||
// just rethrow unchecked
|
// just rethrow unchecked
|
||||||
throw new IllegalStateException(e);
|
throw new IllegalStateException(e);
|
||||||
}
|
}
|
||||||
@ -128,8 +128,9 @@ public class Cloner {
|
|||||||
protected Object fastClone(final Object o, final Map<Object, Object> clones) throws IllegalAccessException {
|
protected Object fastClone(final Object o, final Map<Object, Object> clones) throws IllegalAccessException {
|
||||||
final Class<? extends Object> c = o.getClass();
|
final Class<? extends Object> c = o.getClass();
|
||||||
final IFastCloner fastCloner = fastCloners.get(c);
|
final IFastCloner fastCloner = fastCloners.get(c);
|
||||||
if (fastCloner != null)
|
if (fastCloner != null) {
|
||||||
return fastCloner.clone(o, deepCloner, clones);
|
return fastCloner.clone(o, deepCloner, clones);
|
||||||
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -281,8 +282,9 @@ public class Cloner {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void registerFastCloner(final Class<?> c, final IFastCloner fastCloner) {
|
public void registerFastCloner(final Class<?> c, final IFastCloner fastCloner) {
|
||||||
if (fastCloners.containsKey(c))
|
if (fastCloners.containsKey(c)) {
|
||||||
throw new IllegalArgumentException(c + " already fast-cloned!");
|
throw new IllegalArgumentException(c + " already fast-cloned!");
|
||||||
|
}
|
||||||
fastCloners.put(c, fastCloner);
|
fastCloners.put(c, fastCloner);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -307,8 +309,9 @@ public class Cloner {
|
|||||||
public <T> T fastCloneOrNewInstance(final Class<T> c) {
|
public <T> T fastCloneOrNewInstance(final Class<T> c) {
|
||||||
try {
|
try {
|
||||||
final T fastClone = (T) fastClone(c, null);
|
final T fastClone = (T) fastClone(c, null);
|
||||||
if (fastClone != null)
|
if (fastClone != null) {
|
||||||
return fastClone;
|
return fastClone;
|
||||||
|
}
|
||||||
} catch (final IllegalAccessException e) {
|
} catch (final IllegalAccessException e) {
|
||||||
throw new RuntimeException(e);
|
throw new RuntimeException(e);
|
||||||
}
|
}
|
||||||
@ -326,10 +329,12 @@ public class Cloner {
|
|||||||
* @return a deep-clone of "o".
|
* @return a deep-clone of "o".
|
||||||
*/
|
*/
|
||||||
public <T> T deepClone(final T o) {
|
public <T> T deepClone(final T o) {
|
||||||
if (o == null)
|
if (o == null) {
|
||||||
return null;
|
return null;
|
||||||
if (!cloningEnabled)
|
}
|
||||||
|
if (!cloningEnabled) {
|
||||||
return o;
|
return o;
|
||||||
|
}
|
||||||
if (dumpCloned != null) {
|
if (dumpCloned != null) {
|
||||||
dumpCloned.startCloning(o.getClass());
|
dumpCloned.startCloning(o.getClass());
|
||||||
}
|
}
|
||||||
@ -342,10 +347,12 @@ public class Cloner {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public <T> T deepCloneDontCloneInstances(final T o, final Object... dontCloneThese) {
|
public <T> T deepCloneDontCloneInstances(final T o, final Object... dontCloneThese) {
|
||||||
if (o == null)
|
if (o == null) {
|
||||||
return null;
|
return null;
|
||||||
if (!cloningEnabled)
|
}
|
||||||
|
if (!cloningEnabled) {
|
||||||
return o;
|
return o;
|
||||||
|
}
|
||||||
if (dumpCloned != null) {
|
if (dumpCloned != null) {
|
||||||
dumpCloned.startCloning(o.getClass());
|
dumpCloned.startCloning(o.getClass());
|
||||||
}
|
}
|
||||||
@ -371,10 +378,12 @@ public class Cloner {
|
|||||||
* @return a shallow clone of "o"
|
* @return a shallow clone of "o"
|
||||||
*/
|
*/
|
||||||
public <T> T shallowClone(final T o) {
|
public <T> T shallowClone(final T o) {
|
||||||
if (o == null)
|
if (o == null) {
|
||||||
return null;
|
return null;
|
||||||
if (!cloningEnabled)
|
}
|
||||||
|
if (!cloningEnabled) {
|
||||||
return o;
|
return o;
|
||||||
|
}
|
||||||
try {
|
try {
|
||||||
return cloneInternal(o, null);
|
return cloneInternal(o, null);
|
||||||
} catch (final IllegalAccessException e) {
|
} catch (final IllegalAccessException e) {
|
||||||
@ -411,10 +420,12 @@ public class Cloner {
|
|||||||
*/
|
*/
|
||||||
private boolean isImmutable(final Class<?> clz) {
|
private boolean isImmutable(final Class<?> clz) {
|
||||||
final Boolean isIm = immutables.get(clz);
|
final Boolean isIm = immutables.get(clz);
|
||||||
if (isIm != null)
|
if (isIm != null) {
|
||||||
return isIm;
|
return isIm;
|
||||||
if (considerImmutable(clz))
|
}
|
||||||
|
if (considerImmutable(clz)) {
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
final Class<?> immutableAnnotation = getImmutableAnnotation();
|
final Class<?> immutableAnnotation = getImmutableAnnotation();
|
||||||
for (final Annotation annotation : clz.getDeclaredAnnotations()) {
|
for (final Annotation annotation : clz.getDeclaredAnnotations()) {
|
||||||
@ -442,34 +453,45 @@ public class Cloner {
|
|||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
protected <T> T cloneInternal(final T o, final Map<Object, Object> clones) throws IllegalAccessException {
|
protected <T> T cloneInternal(final T o, final Map<Object, Object> clones) throws IllegalAccessException {
|
||||||
if (o == null)
|
if (o == null) {
|
||||||
return null;
|
return null;
|
||||||
|
}
|
||||||
if (o == this)
|
if (o == this)
|
||||||
|
{
|
||||||
return null; // don't clone the cloner!
|
return null; // don't clone the cloner!
|
||||||
if (ignoredInstances.containsKey(o))
|
}
|
||||||
|
if (ignoredInstances.containsKey(o)) {
|
||||||
return o;
|
return o;
|
||||||
if (o instanceof Enum)
|
}
|
||||||
|
if (o instanceof Enum) {
|
||||||
return o;
|
return o;
|
||||||
|
}
|
||||||
final Class<T> clz = (Class<T>) o.getClass();
|
final Class<T> clz = (Class<T>) o.getClass();
|
||||||
// skip cloning ignored classes
|
// skip cloning ignored classes
|
||||||
if (nullInstead.contains(clz))
|
if (nullInstead.contains(clz)) {
|
||||||
return null;
|
return null;
|
||||||
if (ignored.contains(clz))
|
|
||||||
return o;
|
|
||||||
for (final Class<?> iClz : ignoredInstanceOf) {
|
|
||||||
if (iClz.isAssignableFrom(clz))
|
|
||||||
return o;
|
|
||||||
}
|
}
|
||||||
if (isImmutable(clz))
|
if (ignored.contains(clz)) {
|
||||||
return o;
|
return o;
|
||||||
|
}
|
||||||
|
for (final Class<?> iClz : ignoredInstanceOf) {
|
||||||
|
if (iClz.isAssignableFrom(clz)) {
|
||||||
|
return o;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (isImmutable(clz)) {
|
||||||
|
return o;
|
||||||
|
}
|
||||||
if (o instanceof IFreezable) {
|
if (o instanceof IFreezable) {
|
||||||
final IFreezable f = (IFreezable) o;
|
final IFreezable f = (IFreezable) o;
|
||||||
if (f.isFrozen())
|
if (f.isFrozen()) {
|
||||||
return o;
|
return o;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
final Object clonedPreviously = clones != null ? clones.get(o) : null;
|
final Object clonedPreviously = clones != null ? clones.get(o) : null;
|
||||||
if (clonedPreviously != null)
|
if (clonedPreviously != null) {
|
||||||
return (T) clonedPreviously;
|
return (T) clonedPreviously;
|
||||||
|
}
|
||||||
|
|
||||||
final Object fastClone = fastClone(o, clones);
|
final Object fastClone = fastClone(o, clones);
|
||||||
if (fastClone != null) {
|
if (fastClone != null) {
|
||||||
@ -549,15 +571,18 @@ public class Cloner {
|
|||||||
* fields of src
|
* fields of src
|
||||||
*/
|
*/
|
||||||
public <T, E extends T> void copyPropertiesOfInheritedClass(final T src, final E dest) {
|
public <T, E extends T> void copyPropertiesOfInheritedClass(final T src, final E dest) {
|
||||||
if (src == null)
|
if (src == null) {
|
||||||
throw new IllegalArgumentException("src can't be null");
|
throw new IllegalArgumentException("src can't be null");
|
||||||
if (dest == null)
|
}
|
||||||
|
if (dest == null) {
|
||||||
throw new IllegalArgumentException("dest can't be null");
|
throw new IllegalArgumentException("dest can't be null");
|
||||||
|
}
|
||||||
final Class<? extends Object> srcClz = src.getClass();
|
final Class<? extends Object> srcClz = src.getClass();
|
||||||
final Class<? extends Object> destClz = dest.getClass();
|
final Class<? extends Object> destClz = dest.getClass();
|
||||||
if (srcClz.isArray()) {
|
if (srcClz.isArray()) {
|
||||||
if (!destClz.isArray())
|
if (!destClz.isArray()) {
|
||||||
throw new IllegalArgumentException("can't copy from array to non-array class " + destClz);
|
throw new IllegalArgumentException("can't copy from array to non-array class " + destClz);
|
||||||
|
}
|
||||||
final int length = Array.getLength(src);
|
final int length = Array.getLength(src);
|
||||||
for (int i = 0; i < length; i++) {
|
for (int i = 0; i < length; i++) {
|
||||||
final Object v = Array.get(src, i);
|
final Object v = Array.get(src, i);
|
||||||
@ -639,8 +664,9 @@ public class Cloner {
|
|||||||
System.out.println("cloned field>" + field + " -- of class " + clz);
|
System.out.println("cloned field>" + field + " -- of class " + clz);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
} else
|
} else {
|
||||||
dumpCloned = null;
|
dumpCloned = null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isCloningEnabled() {
|
public boolean isCloningEnabled() {
|
||||||
|
@ -14,7 +14,7 @@ public class FastClonerCalendar implements IFastCloner {
|
|||||||
@Override
|
@Override
|
||||||
public Object clone(final Object t, final IDeepCloner cloner, final Map<Object, Object> clones) {
|
public Object clone(final Object t, final IDeepCloner cloner, final Map<Object, Object> clones) {
|
||||||
final GregorianCalendar gc = new GregorianCalendar();
|
final GregorianCalendar gc = new GregorianCalendar();
|
||||||
Calendar c = (Calendar) t;
|
final Calendar c = (Calendar) t;
|
||||||
gc.setTimeInMillis(c.getTimeInMillis());
|
gc.setTimeInMillis(c.getTimeInMillis());
|
||||||
gc.setTimeZone((TimeZone) c.getTimeZone().clone());
|
gc.setTimeZone((TimeZone) c.getTimeZone().clone());
|
||||||
return gc;
|
return gc;
|
||||||
|
@ -43,10 +43,12 @@ public class Perspectives {
|
|||||||
* @return the E perspective of o
|
* @return the E perspective of o
|
||||||
*/
|
*/
|
||||||
public <T, E extends T> E viewAs(final Class<E> c, final T o) {
|
public <T, E extends T> E viewAs(final Class<E> c, final T o) {
|
||||||
if (o == null)
|
if (o == null) {
|
||||||
return null;
|
return null;
|
||||||
if (o instanceof Collection<?>)
|
}
|
||||||
|
if (o instanceof Collection<?>) {
|
||||||
throw new IllegalArgumentException("for collections please use viewCollectionAs() method. Invalid object " + o);
|
throw new IllegalArgumentException("for collections please use viewCollectionAs() method. Invalid object " + o);
|
||||||
|
}
|
||||||
final E newInstance = cloner.fastCloneOrNewInstance(c);
|
final E newInstance = cloner.fastCloneOrNewInstance(c);
|
||||||
cloner.copyPropertiesOfInheritedClass(o, newInstance);
|
cloner.copyPropertiesOfInheritedClass(o, newInstance);
|
||||||
return newInstance;
|
return newInstance;
|
||||||
@ -81,8 +83,9 @@ public class Perspectives {
|
|||||||
*/
|
*/
|
||||||
public <I, NI extends I, T extends Collection<I>, E extends Collection<NI>> E viewCollectionAs(
|
public <I, NI extends I, T extends Collection<I>, E extends Collection<NI>> E viewCollectionAs(
|
||||||
final E newCollection, final Class<NI> perspectiveCollectionItemClass, final T currentCollection) {
|
final E newCollection, final Class<NI> perspectiveCollectionItemClass, final T currentCollection) {
|
||||||
if (currentCollection == null)
|
if (currentCollection == null) {
|
||||||
return null;
|
return null;
|
||||||
|
}
|
||||||
for (final I item : currentCollection) {
|
for (final I item : currentCollection) {
|
||||||
final NI newItem = viewAs(perspectiveCollectionItemClass, item);
|
final NI newItem = viewAs(perspectiveCollectionItemClass, item);
|
||||||
newCollection.add(newItem);
|
newCollection.add(newItem);
|
||||||
|
@ -35,11 +35,12 @@ public class Bernoulli {
|
|||||||
*/
|
*/
|
||||||
protected void set(final int n, final Rational value) {
|
protected void set(final int n, final Rational value) {
|
||||||
final int nindx = n / 2;
|
final int nindx = n / 2;
|
||||||
if (nindx < a.size())
|
if (nindx < a.size()) {
|
||||||
a.set(nindx, value);
|
a.set(nindx, value);
|
||||||
else {
|
} else {
|
||||||
while (a.size() < nindx)
|
while (a.size() < nindx) {
|
||||||
a.add(Rational.ZERO);
|
a.add(Rational.ZERO);
|
||||||
|
}
|
||||||
a.add(value);
|
a.add(value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -53,15 +54,16 @@ public class Bernoulli {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public Rational at(int n) throws Error {
|
public Rational at(int n) throws Error {
|
||||||
if (n == 1)
|
if (n == 1) {
|
||||||
return (new Rational(-1, 2));
|
return (new Rational(-1, 2));
|
||||||
else if (n % 2 != 0)
|
} else if (n % 2 != 0) {
|
||||||
return Rational.ZERO;
|
return Rational.ZERO;
|
||||||
else {
|
} else {
|
||||||
final int nindx = n / 2;
|
final int nindx = n / 2;
|
||||||
if (a.size() <= nindx) {
|
if (a.size() <= nindx) {
|
||||||
for (int i = 2 * a.size(); i <= n; i += 2)
|
for (int i = 2 * a.size(); i <= n; i += 2) {
|
||||||
set(i, doubleSum(i));
|
set(i, doubleSum(i));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return a.elementAt(nindx);
|
return a.elementAt(nindx);
|
||||||
}
|
}
|
||||||
@ -80,11 +82,12 @@ public class Bernoulli {
|
|||||||
Rational jsum = Rational.ZERO;
|
Rational jsum = Rational.ZERO;
|
||||||
BigInteger bin = BigInteger.ONE;
|
BigInteger bin = BigInteger.ONE;
|
||||||
for (int j = 0; j <= k; j++) {
|
for (int j = 0; j <= k; j++) {
|
||||||
BigInteger jpown = (new BigInteger("" + j)).pow(n);
|
final BigInteger jpown = (new BigInteger("" + j)).pow(n);
|
||||||
if (j % 2 == 0)
|
if (j % 2 == 0) {
|
||||||
jsum = jsum.add(bin.multiply(jpown));
|
jsum = jsum.add(bin.multiply(jpown));
|
||||||
else
|
} else {
|
||||||
jsum = jsum.subtract(bin.multiply(jpown));
|
jsum = jsum.subtract(bin.multiply(jpown));
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* update binomial(k,j) recursively
|
* update binomial(k,j) recursively
|
||||||
|
@ -165,14 +165,16 @@ public class BigComplex {
|
|||||||
* and v= +- sqrt((l-re)/2 as the new real and imaginary parts.
|
* and v= +- sqrt((l-re)/2 as the new real and imaginary parts.
|
||||||
*/
|
*/
|
||||||
final BigDecimal l = abs(mc);
|
final BigDecimal l = abs(mc);
|
||||||
if (l.compareTo(BigDecimal.ZERO) == 0)
|
if (l.compareTo(BigDecimal.ZERO) == 0) {
|
||||||
return new BigComplex(BigDecimalMath.scalePrec(BigDecimal.ZERO, mc), BigDecimalMath.scalePrec(BigDecimal.ZERO, mc));
|
return new BigComplex(BigDecimalMath.scalePrec(BigDecimal.ZERO, mc), BigDecimalMath.scalePrec(BigDecimal.ZERO, mc));
|
||||||
|
}
|
||||||
final BigDecimal u = BigDecimalMath.sqrt(l.add(re).divide(half, mc), mc);
|
final BigDecimal u = BigDecimalMath.sqrt(l.add(re).divide(half, mc), mc);
|
||||||
final BigDecimal v = BigDecimalMath.sqrt(l.subtract(re).divide(half, mc), mc);
|
final BigDecimal v = BigDecimalMath.sqrt(l.subtract(re).divide(half, mc), mc);
|
||||||
if (im.compareTo(BigDecimal.ZERO) >= 0)
|
if (im.compareTo(BigDecimal.ZERO) >= 0) {
|
||||||
return new BigComplex(u, v);
|
return new BigComplex(u, v);
|
||||||
else
|
} else {
|
||||||
return new BigComplex(u, v.negate());
|
return new BigComplex(u, v.negate());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -23,14 +23,17 @@ public class BigIntegerMath {
|
|||||||
* @return The binomial coefficient
|
* @return The binomial coefficient
|
||||||
*/
|
*/
|
||||||
static public BigInteger binomial(final int n, final int k) {
|
static public BigInteger binomial(final int n, final int k) {
|
||||||
if (k == 0)
|
if (k == 0) {
|
||||||
return (BigInteger.ONE);
|
return (BigInteger.ONE);
|
||||||
|
}
|
||||||
BigInteger bin = new BigInteger("" + n);
|
BigInteger bin = new BigInteger("" + n);
|
||||||
BigInteger n2 = bin;
|
final BigInteger n2 = bin;
|
||||||
for (BigInteger i = new BigInteger("" + (k - 1)); i.compareTo(BigInteger.ONE) >= 0; i = i.subtract(BigInteger.ONE))
|
for (BigInteger i = new BigInteger("" + (k - 1)); i.compareTo(BigInteger.ONE) >= 0; i = i.subtract(BigInteger.ONE)) {
|
||||||
bin = bin.multiply(n2.subtract(i));
|
bin = bin.multiply(n2.subtract(i));
|
||||||
for (BigInteger i = new BigInteger("" + k); i.compareTo(BigInteger.ONE) == 1; i = i.subtract(BigInteger.ONE))
|
}
|
||||||
|
for (BigInteger i = new BigInteger("" + k); i.compareTo(BigInteger.ONE) == 1; i = i.subtract(BigInteger.ONE)) {
|
||||||
bin = bin.divide(i);
|
bin = bin.divide(i);
|
||||||
|
}
|
||||||
return (bin);
|
return (bin);
|
||||||
} /* binomial */
|
} /* binomial */
|
||||||
|
|
||||||
@ -48,8 +51,9 @@ public class BigIntegerMath {
|
|||||||
/*
|
/*
|
||||||
* binomial(n,0) =1
|
* binomial(n,0) =1
|
||||||
*/
|
*/
|
||||||
if (k.compareTo(BigInteger.ZERO) == 0)
|
if (k.compareTo(BigInteger.ZERO) == 0) {
|
||||||
return (BigInteger.ONE);
|
return (BigInteger.ONE);
|
||||||
|
}
|
||||||
|
|
||||||
BigInteger bin = new BigInteger("" + n);
|
BigInteger bin = new BigInteger("" + n);
|
||||||
|
|
||||||
@ -78,8 +82,9 @@ public class BigIntegerMath {
|
|||||||
* and in the integer domain. First replace C(n,k) by C(n,n-k) if n-k<k.
|
* and in the integer domain. First replace C(n,k) by C(n,n-k) if n-k<k.
|
||||||
*/
|
*/
|
||||||
BigInteger truek = new BigInteger(k.toString());
|
BigInteger truek = new BigInteger(k.toString());
|
||||||
if (n.subtract(k).compareTo(k) < 0)
|
if (n.subtract(k).compareTo(k) < 0) {
|
||||||
truek = n.subtract(k);
|
truek = n.subtract(k);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Calculate C(num,truek) where num=n and truek is the smaller of n-k
|
* Calculate C(num,truek) where num=n and truek is the smaller of n-k
|
||||||
@ -168,8 +173,9 @@ public class BigIntegerMath {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
static public int isqrt(final int n) {
|
static public int isqrt(final int n) {
|
||||||
if (n < 0)
|
if (n < 0) {
|
||||||
throw new ArithmeticException("Negative argument " + n);
|
throw new ArithmeticException("Negative argument " + n);
|
||||||
|
}
|
||||||
final double resul = Math.sqrt(n);
|
final double resul = Math.sqrt(n);
|
||||||
return (int) Math.round(resul);
|
return (int) Math.round(resul);
|
||||||
}
|
}
|
||||||
@ -185,8 +191,9 @@ public class BigIntegerMath {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
static public long isqrt(final long n) {
|
static public long isqrt(final long n) {
|
||||||
if (n < 0)
|
if (n < 0) {
|
||||||
throw new ArithmeticException("Negative argument " + n);
|
throw new ArithmeticException("Negative argument " + n);
|
||||||
|
}
|
||||||
final double resul = Math.sqrt(n);
|
final double resul = Math.sqrt(n);
|
||||||
return Math.round(resul);
|
return Math.round(resul);
|
||||||
}
|
}
|
||||||
@ -202,16 +209,17 @@ public class BigIntegerMath {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
static public BigInteger isqrt(final BigInteger n) {
|
static public BigInteger isqrt(final BigInteger n) {
|
||||||
if (n.compareTo(BigInteger.ZERO) < 0)
|
if (n.compareTo(BigInteger.ZERO) < 0) {
|
||||||
throw new ArithmeticException("Negative argument " + n.toString());
|
throw new ArithmeticException("Negative argument " + n.toString());
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* Start with an estimate from a floating point reduction.
|
* Start with an estimate from a floating point reduction.
|
||||||
*/
|
*/
|
||||||
BigInteger x;
|
BigInteger x;
|
||||||
final int bl = n.bitLength();
|
final int bl = n.bitLength();
|
||||||
if (bl > 120)
|
if (bl > 120) {
|
||||||
x = n.shiftRight(bl / 2 - 1);
|
x = n.shiftRight(bl / 2 - 1);
|
||||||
else {
|
} else {
|
||||||
final double resul = Math.sqrt(n.doubleValue());
|
final double resul = Math.sqrt(n.doubleValue());
|
||||||
x = new BigInteger("" + Math.round(resul));
|
x = new BigInteger("" + Math.round(resul));
|
||||||
}
|
}
|
||||||
@ -221,13 +229,15 @@ public class BigIntegerMath {
|
|||||||
/*
|
/*
|
||||||
* check whether the result is accurate, x^2 =n
|
* check whether the result is accurate, x^2 =n
|
||||||
*/
|
*/
|
||||||
BigInteger x2 = x.pow(2);
|
final BigInteger x2 = x.pow(2);
|
||||||
BigInteger xplus2 = x.add(BigInteger.ONE).pow(2);
|
BigInteger xplus2 = x.add(BigInteger.ONE).pow(2);
|
||||||
if (x2.compareTo(n) <= 0 && xplus2.compareTo(n) > 0)
|
if (x2.compareTo(n) <= 0 && xplus2.compareTo(n) > 0) {
|
||||||
return x;
|
return x;
|
||||||
|
}
|
||||||
xplus2 = xplus2.subtract(x.shiftLeft(2));
|
xplus2 = xplus2.subtract(x.shiftLeft(2));
|
||||||
if (xplus2.compareTo(n) <= 0 && x2.compareTo(n) > 0)
|
if (xplus2.compareTo(n) <= 0 && x2.compareTo(n) > 0) {
|
||||||
return x.subtract(BigInteger.ONE);
|
return x.subtract(BigInteger.ONE);
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* Newton algorithm. This correction is on the
|
* Newton algorithm. This correction is on the
|
||||||
* low side caused by the integer divisions. So the value required
|
* low side caused by the integer divisions. So the value required
|
||||||
@ -251,8 +261,9 @@ public class BigIntegerMath {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
static public BigInteger core(final BigInteger n) {
|
static public BigInteger core(final BigInteger n) {
|
||||||
if (n.compareTo(BigInteger.ZERO) < 0)
|
if (n.compareTo(BigInteger.ZERO) < 0) {
|
||||||
throw new ArithmeticException("Negative argument " + n);
|
throw new ArithmeticException("Negative argument " + n);
|
||||||
|
}
|
||||||
final Ifactor i = new Ifactor(n);
|
final Ifactor i = new Ifactor(n);
|
||||||
return i.core();
|
return i.core();
|
||||||
}
|
}
|
||||||
@ -278,17 +289,21 @@ public class BigIntegerMath {
|
|||||||
static public BigInteger[][] minor(final BigInteger[][] A, final int r, final int c) throws ArithmeticException {
|
static public BigInteger[][] minor(final BigInteger[][] A, final int r, final int c) throws ArithmeticException {
|
||||||
/* original row count */
|
/* original row count */
|
||||||
final int rL = A.length;
|
final int rL = A.length;
|
||||||
if (rL == 0)
|
if (rL == 0) {
|
||||||
throw new ArithmeticException("zero row count in matrix");
|
throw new ArithmeticException("zero row count in matrix");
|
||||||
if (r < 0 || r >= rL)
|
}
|
||||||
|
if (r < 0 || r >= rL) {
|
||||||
throw new ArithmeticException("row number " + r + " out of range 0.." + (rL - 1));
|
throw new ArithmeticException("row number " + r + " out of range 0.." + (rL - 1));
|
||||||
|
}
|
||||||
/* original column count */
|
/* original column count */
|
||||||
final int cL = A[0].length;
|
final int cL = A[0].length;
|
||||||
if (cL == 0)
|
if (cL == 0) {
|
||||||
throw new ArithmeticException("zero column count in matrix");
|
throw new ArithmeticException("zero column count in matrix");
|
||||||
if (c < 0 || c >= cL)
|
}
|
||||||
|
if (c < 0 || c >= cL) {
|
||||||
throw new ArithmeticException("column number " + c + " out of range 0.." + (cL - 1));
|
throw new ArithmeticException("column number " + c + " out of range 0.." + (cL - 1));
|
||||||
BigInteger M[][] = new BigInteger[rL - 1][cL - 1];
|
}
|
||||||
|
final BigInteger M[][] = new BigInteger[rL - 1][cL - 1];
|
||||||
int imrow = 0;
|
int imrow = 0;
|
||||||
for (int row = 0; row < rL; row++) {
|
for (int row = 0; row < rL; row++) {
|
||||||
if (row != r) {
|
if (row != r) {
|
||||||
@ -327,15 +342,18 @@ public class BigIntegerMath {
|
|||||||
throws ArithmeticException {
|
throws ArithmeticException {
|
||||||
/* original row count */
|
/* original row count */
|
||||||
final int rL = A.length;
|
final int rL = A.length;
|
||||||
if (rL == 0)
|
if (rL == 0) {
|
||||||
throw new ArithmeticException("zero row count in matrix");
|
throw new ArithmeticException("zero row count in matrix");
|
||||||
|
}
|
||||||
/* original column count */
|
/* original column count */
|
||||||
final int cL = A[0].length;
|
final int cL = A[0].length;
|
||||||
if (cL == 0)
|
if (cL == 0) {
|
||||||
throw new ArithmeticException("zero column count in matrix");
|
throw new ArithmeticException("zero column count in matrix");
|
||||||
if (c < 0 || c >= cL)
|
}
|
||||||
|
if (c < 0 || c >= cL) {
|
||||||
throw new ArithmeticException("column number " + c + " out of range 0.." + (cL - 1));
|
throw new ArithmeticException("column number " + c + " out of range 0.." + (cL - 1));
|
||||||
BigInteger M[][] = new BigInteger[rL][cL];
|
}
|
||||||
|
final BigInteger M[][] = new BigInteger[rL][cL];
|
||||||
for (int row = 0; row < rL; row++) {
|
for (int row = 0; row < rL; row++) {
|
||||||
for (int col = 0; col < cL; col++) {
|
for (int col = 0; col < cL; col++) {
|
||||||
/*
|
/*
|
||||||
@ -343,10 +361,11 @@ public class BigIntegerMath {
|
|||||||
* surplus
|
* surplus
|
||||||
* elements will be ignored. Shorter v lead to an exception.
|
* elements will be ignored. Shorter v lead to an exception.
|
||||||
*/
|
*/
|
||||||
if (col != c)
|
if (col != c) {
|
||||||
M[row][col] = A[row][col];
|
M[row][col] = A[row][col];
|
||||||
else
|
} else {
|
||||||
M[row][col] = v[row];
|
M[row][col] = v[row];
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return M;
|
return M;
|
||||||
@ -367,20 +386,21 @@ public class BigIntegerMath {
|
|||||||
BigInteger d = BigInteger.ZERO;
|
BigInteger d = BigInteger.ZERO;
|
||||||
/* row size */
|
/* row size */
|
||||||
final int rL = A.length;
|
final int rL = A.length;
|
||||||
if (rL == 0)
|
if (rL == 0) {
|
||||||
throw new ArithmeticException("zero row count in matrix");
|
throw new ArithmeticException("zero row count in matrix");
|
||||||
|
}
|
||||||
/* column size */
|
/* column size */
|
||||||
final int cL = A[0].length;
|
final int cL = A[0].length;
|
||||||
if (cL != rL)
|
if (cL != rL) {
|
||||||
throw new ArithmeticException("Non-square matrix dim " + rL + " by " + cL);
|
throw new ArithmeticException("Non-square matrix dim " + rL + " by " + cL);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Compute the low-order cases directly.
|
* Compute the low-order cases directly.
|
||||||
*/
|
*/
|
||||||
if (rL == 1)
|
if (rL == 1) {
|
||||||
return A[0][0];
|
return A[0][0];
|
||||||
|
} else if (rL == 2) {
|
||||||
else if (rL == 2) {
|
|
||||||
d = A[0][0].multiply(A[1][1]);
|
d = A[0][0].multiply(A[1][1]);
|
||||||
return d.subtract(A[0][1].multiply(A[1][0]));
|
return d.subtract(A[0][1].multiply(A[1][0]));
|
||||||
} else {
|
} else {
|
||||||
@ -393,10 +413,11 @@ public class BigIntegerMath {
|
|||||||
final BigInteger M[][] = minor(A, r, 0);
|
final BigInteger M[][] = minor(A, r, 0);
|
||||||
final BigInteger m = A[r][0].multiply(det(M));
|
final BigInteger m = A[r][0].multiply(det(M));
|
||||||
/* recursive call */
|
/* recursive call */
|
||||||
if (r % 2 == 0)
|
if (r % 2 == 0) {
|
||||||
d = d.add(m);
|
d = d.add(m);
|
||||||
else
|
} else {
|
||||||
d = d.subtract(m);
|
d = d.subtract(m);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -421,26 +442,30 @@ public class BigIntegerMath {
|
|||||||
static public Rational[] solve(final BigInteger[][] A, final BigInteger[] rhs) throws ArithmeticException, Error {
|
static public Rational[] solve(final BigInteger[][] A, final BigInteger[] rhs) throws ArithmeticException, Error {
|
||||||
|
|
||||||
final int rL = A.length;
|
final int rL = A.length;
|
||||||
if (rL == 0)
|
if (rL == 0) {
|
||||||
throw new ArithmeticException("zero row count in matrix");
|
throw new ArithmeticException("zero row count in matrix");
|
||||||
|
}
|
||||||
|
|
||||||
/* column size */
|
/* column size */
|
||||||
final int cL = A[0].length;
|
final int cL = A[0].length;
|
||||||
if (cL != rL)
|
if (cL != rL) {
|
||||||
throw new ArithmeticException("Non-square matrix dim " + rL + " by " + cL);
|
throw new ArithmeticException("Non-square matrix dim " + rL + " by " + cL);
|
||||||
if (rhs.length != rL)
|
}
|
||||||
|
if (rhs.length != rL) {
|
||||||
throw new ArithmeticException("Right hand side dim " + rhs.length + " unequal matrix dim " + rL);
|
throw new ArithmeticException("Right hand side dim " + rhs.length + " unequal matrix dim " + rL);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Gauss elimination
|
* Gauss elimination
|
||||||
*/
|
*/
|
||||||
Rational x[] = new Rational[rL];
|
final Rational x[] = new Rational[rL];
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* copy of r.h.s ito a mutable Rationalright hand side
|
* copy of r.h.s ito a mutable Rationalright hand side
|
||||||
*/
|
*/
|
||||||
for (int c = 0; c < cL; c++)
|
for (int c = 0; c < cL; c++) {
|
||||||
x[c] = new Rational(rhs[c]);
|
x[c] = new Rational(rhs[c]);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Create zeros downwards column c by linear combination of row c and
|
* Create zeros downwards column c by linear combination of row c and
|
||||||
@ -456,11 +481,11 @@ public class BigIntegerMath {
|
|||||||
for (int r = c + 1; r < rL; r++) {
|
for (int r = c + 1; r < rL; r++) {
|
||||||
if (A[r][c].compareTo(BigInteger.ZERO) != 0) {
|
if (A[r][c].compareTo(BigInteger.ZERO) != 0) {
|
||||||
for (int cpr = c; cpr < cL; cpr++) {
|
for (int cpr = c; cpr < cL; cpr++) {
|
||||||
BigInteger tmp = A[c][cpr];
|
final BigInteger tmp = A[c][cpr];
|
||||||
A[c][cpr] = A[r][cpr];
|
A[c][cpr] = A[r][cpr];
|
||||||
A[r][cpr] = tmp;
|
A[r][cpr] = tmp;
|
||||||
}
|
}
|
||||||
Rational tmp = x[c];
|
final Rational tmp = x[c];
|
||||||
x[c] = x[r];
|
x[c] = x[r];
|
||||||
x[r] = tmp;
|
x[r] = tmp;
|
||||||
swpd = true;
|
swpd = true;
|
||||||
@ -471,8 +496,9 @@ public class BigIntegerMath {
|
|||||||
* not swapped with a non-zero row: determinant zero and no
|
* not swapped with a non-zero row: determinant zero and no
|
||||||
* solution
|
* solution
|
||||||
*/
|
*/
|
||||||
if (!swpd)
|
if (!swpd) {
|
||||||
throw new ArithmeticException("Zero determinant of main matrix");
|
throw new ArithmeticException("Zero determinant of main matrix");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
/* create zero at A[c+1..cL-1][c] */
|
/* create zero at A[c+1..cL-1][c] */
|
||||||
for (int r = c + 1; r < rL; r++) {
|
for (int r = c + 1; r < rL; r++) {
|
||||||
@ -481,20 +507,22 @@ public class BigIntegerMath {
|
|||||||
* not visited again
|
* not visited again
|
||||||
*/
|
*/
|
||||||
for (int cpr = c + 1; cpr < cL; cpr++) {
|
for (int cpr = c + 1; cpr < cL; cpr++) {
|
||||||
BigInteger tmp = A[c][c].multiply(A[r][cpr]).subtract(A[c][cpr].multiply(A[r][c]));
|
final BigInteger tmp = A[c][c].multiply(A[r][cpr]).subtract(A[c][cpr].multiply(A[r][c]));
|
||||||
A[r][cpr] = tmp;
|
A[r][cpr] = tmp;
|
||||||
}
|
}
|
||||||
Rational tmp = x[r].multiply(A[c][c]).subtract(x[c].multiply(A[r][c]));
|
final Rational tmp = x[r].multiply(A[c][c]).subtract(x[c].multiply(A[r][c]));
|
||||||
x[r] = tmp;
|
x[r] = tmp;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (A[cL - 1][cL - 1].compareTo(BigInteger.ZERO) == 0)
|
if (A[cL - 1][cL - 1].compareTo(BigInteger.ZERO) == 0) {
|
||||||
throw new ArithmeticException("Zero determinant of main matrix");
|
throw new ArithmeticException("Zero determinant of main matrix");
|
||||||
|
}
|
||||||
/* backward elimination */
|
/* backward elimination */
|
||||||
for (int r = cL - 1; r >= 0; r--) {
|
for (int r = cL - 1; r >= 0; r--) {
|
||||||
x[r] = x[r].divide(A[r][r]);
|
x[r] = x[r].divide(A[r][r]);
|
||||||
for (int rpr = r - 1; rpr >= 0; rpr--)
|
for (int rpr = r - 1; rpr >= 0; rpr--) {
|
||||||
x[rpr] = x[rpr].subtract(x[r].multiply(A[rpr][r]));
|
x[rpr] = x[rpr].subtract(x[r].multiply(A[rpr][r]));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return x;
|
return x;
|
||||||
@ -512,7 +540,7 @@ public class BigIntegerMath {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
static public BigInteger lcm(final BigInteger a, final BigInteger b) {
|
static public BigInteger lcm(final BigInteger a, final BigInteger b) {
|
||||||
BigInteger g = a.gcd(b);
|
final BigInteger g = a.gcd(b);
|
||||||
return a.multiply(b).abs().divide(g);
|
return a.multiply(b).abs().divide(g);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -529,11 +557,13 @@ public class BigIntegerMath {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
static public BigInteger valueOf(final Vector<BigInteger> c, final BigInteger x) {
|
static public BigInteger valueOf(final Vector<BigInteger> c, final BigInteger x) {
|
||||||
if (c.size() == 0)
|
if (c.size() == 0) {
|
||||||
return BigInteger.ZERO;
|
return BigInteger.ZERO;
|
||||||
|
}
|
||||||
BigInteger res = c.lastElement();
|
BigInteger res = c.lastElement();
|
||||||
for (int i = c.size() - 2; i >= 0; i--)
|
for (int i = c.size() - 2; i >= 0; i--) {
|
||||||
res = res.multiply(x).add(c.elementAt(i));
|
res = res.multiply(x).add(c.elementAt(i));
|
||||||
|
}
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -552,32 +582,34 @@ public class BigIntegerMath {
|
|||||||
* et al, Num. Funct. Anal. Opt. 10 (5)( 1989) 419-488</a>
|
* et al, Num. Funct. Anal. Opt. 10 (5)( 1989) 419-488</a>
|
||||||
*/
|
*/
|
||||||
static public Rational centrlFactNumt(int n, int k) throws Error {
|
static public Rational centrlFactNumt(int n, int k) throws Error {
|
||||||
if (k > n || k < 0 || (k % 2) != (n % 2))
|
if (k > n || k < 0 || (k % 2) != (n % 2)) {
|
||||||
return Rational.ZERO;
|
return Rational.ZERO;
|
||||||
else if (k == n)
|
} else if (k == n) {
|
||||||
return Rational.ONE;
|
return Rational.ONE;
|
||||||
else {
|
} else {
|
||||||
/* Proposition 6.2.6 */
|
/* Proposition 6.2.6 */
|
||||||
Factorial f = new Factorial();
|
final Factorial f = new Factorial();
|
||||||
Rational jsum = new Rational(0, 1);
|
Rational jsum = new Rational(0, 1);
|
||||||
int kprime = n - k;
|
final int kprime = n - k;
|
||||||
for (int j = 0; j <= kprime; j++) {
|
for (int j = 0; j <= kprime; j++) {
|
||||||
Rational nusum = new Rational(0, 1);
|
Rational nusum = new Rational(0, 1);
|
||||||
for (int nu = 0; nu <= j; nu++) {
|
for (int nu = 0; nu <= j; nu++) {
|
||||||
Rational t = new Rational(j - 2 * nu, 2);
|
Rational t = new Rational(j - 2 * nu, 2);
|
||||||
t = t.pow(kprime + j);
|
t = t.pow(kprime + j);
|
||||||
t = t.multiply(binomial(j, nu));
|
t = t.multiply(binomial(j, nu));
|
||||||
if (nu % 2 != 0)
|
if (nu % 2 != 0) {
|
||||||
nusum = nusum.subtract(t);
|
nusum = nusum.subtract(t);
|
||||||
else
|
} else {
|
||||||
nusum = nusum.add(t);
|
nusum = nusum.add(t);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
nusum = nusum.divide(f.at(j)).divide(n + j);
|
nusum = nusum.divide(f.at(j)).divide(n + j);
|
||||||
nusum = nusum.multiply(binomial(2 * kprime, kprime - j));
|
nusum = nusum.multiply(binomial(2 * kprime, kprime - j));
|
||||||
if (j % 2 != 0)
|
if (j % 2 != 0) {
|
||||||
jsum = jsum.subtract(nusum);
|
jsum = jsum.subtract(nusum);
|
||||||
else
|
} else {
|
||||||
jsum = jsum.add(nusum);
|
jsum = jsum.add(nusum);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return jsum.multiply(k).multiply(binomial(n + kprime, k));
|
return jsum.multiply(k).multiply(binomial(n + kprime, k));
|
||||||
}
|
}
|
||||||
@ -597,11 +629,11 @@ public class BigIntegerMath {
|
|||||||
* et al, Num. Funct. Anal. Opt. 10 (5)( 1989) 419-488</a>
|
* et al, Num. Funct. Anal. Opt. 10 (5)( 1989) 419-488</a>
|
||||||
*/
|
*/
|
||||||
static public Rational centrlFactNumT(int n, int k) {
|
static public Rational centrlFactNumT(int n, int k) {
|
||||||
if (k > n || k < 0 || (k % 2) != (n % 2))
|
if (k > n || k < 0 || (k % 2) != (n % 2)) {
|
||||||
return Rational.ZERO;
|
return Rational.ZERO;
|
||||||
else if (k == n)
|
} else if (k == n) {
|
||||||
return Rational.ONE;
|
return Rational.ONE;
|
||||||
else {
|
} else {
|
||||||
/* Proposition 2.1 */
|
/* Proposition 2.1 */
|
||||||
return centrlFactNumT(n - 2, k - 2).add(centrlFactNumT(n - 2, k).multiply(new Rational(k * k, 4)));
|
return centrlFactNumT(n - 2, k - 2).add(centrlFactNumT(n - 2, k).multiply(new Rational(k * k, 4)));
|
||||||
}
|
}
|
||||||
|
@ -39,10 +39,11 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
*/
|
*/
|
||||||
public BigIntegerPoly(final String L) throws NumberFormatException {
|
public BigIntegerPoly(final String L) throws NumberFormatException {
|
||||||
a = new Vector<>();
|
a = new Vector<>();
|
||||||
Scanner sc = new Scanner(L);
|
final Scanner sc = new Scanner(L);
|
||||||
sc.useDelimiter(",");
|
sc.useDelimiter(",");
|
||||||
while (sc.hasNextBigInteger())
|
while (sc.hasNextBigInteger()) {
|
||||||
a.add(sc.nextBigInteger());
|
a.add(sc.nextBigInteger());
|
||||||
|
}
|
||||||
simplify();
|
simplify();
|
||||||
sc.close();
|
sc.close();
|
||||||
} /* ctor */
|
} /* ctor */
|
||||||
@ -66,8 +67,9 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* The coefficients a0, a1, a2 etc in a0+a1*x+a2*x^2+...
|
* The coefficients a0, a1, a2 etc in a0+a1*x+a2*x^2+...
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly(final BigInteger[] c) {
|
public BigIntegerPoly(final BigInteger[] c) {
|
||||||
for (int i = 0; i < c.length; i++)
|
for (final BigInteger element : c) {
|
||||||
a.add(c[i].add(BigInteger.ZERO));
|
a.add(element.add(BigInteger.ZERO));
|
||||||
|
}
|
||||||
simplify();
|
simplify();
|
||||||
} /* ctor */
|
} /* ctor */
|
||||||
|
|
||||||
@ -87,9 +89,10 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2012-03-02
|
* @since 2012-03-02
|
||||||
*/
|
*/
|
||||||
public RatPoly toRatPoly() {
|
public RatPoly toRatPoly() {
|
||||||
RatPoly bd = new RatPoly();
|
final RatPoly bd = new RatPoly();
|
||||||
for (int i = 0; i < a.size(); i++)
|
for (int i = 0; i < a.size(); i++) {
|
||||||
bd.set(i, a.elementAt(i));
|
bd.set(i, a.elementAt(i));
|
||||||
|
}
|
||||||
return bd;
|
return bd;
|
||||||
} /* toRatPoly */
|
} /* toRatPoly */
|
||||||
|
|
||||||
@ -102,10 +105,11 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @return the polynomial coefficient in front of x^n.
|
* @return the polynomial coefficient in front of x^n.
|
||||||
*/
|
*/
|
||||||
public BigInteger at(final int n) {
|
public BigInteger at(final int n) {
|
||||||
if (n < a.size())
|
if (n < a.size()) {
|
||||||
return (a.elementAt(n));
|
return (a.elementAt(n));
|
||||||
else
|
} else {
|
||||||
return (BigInteger.ZERO);
|
return (BigInteger.ZERO);
|
||||||
|
}
|
||||||
} /* at */
|
} /* at */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -118,14 +122,16 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
public BigInteger valueOf(final BigInteger x) {
|
public BigInteger valueOf(final BigInteger x) {
|
||||||
if (a.size() == 0)
|
if (a.size() == 0) {
|
||||||
return BigInteger.ZERO;
|
return BigInteger.ZERO;
|
||||||
|
}
|
||||||
BigInteger res = a.lastElement();
|
BigInteger res = a.lastElement();
|
||||||
/*
|
/*
|
||||||
* Heron casted form
|
* Heron casted form
|
||||||
*/
|
*/
|
||||||
for (int i = a.size() - 2; i >= 0; i--)
|
for (int i = a.size() - 2; i >= 0; i--) {
|
||||||
res = res.multiply(x).add(a.elementAt(i));
|
res = res.multiply(x).add(a.elementAt(i));
|
||||||
|
}
|
||||||
return res;
|
return res;
|
||||||
} /* valueOf */
|
} /* valueOf */
|
||||||
|
|
||||||
@ -154,9 +160,9 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* the new value of the coefficient.
|
* the new value of the coefficient.
|
||||||
*/
|
*/
|
||||||
public void set(final int n, final BigInteger value) {
|
public void set(final int n, final BigInteger value) {
|
||||||
if (n < a.size())
|
if (n < a.size()) {
|
||||||
a.set(n, value);
|
a.set(n, value);
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* fill intermediate powers with coefficients of zero
|
* fill intermediate powers with coefficients of zero
|
||||||
*/
|
*/
|
||||||
@ -180,7 +186,7 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* the new value of the coefficient.
|
* the new value of the coefficient.
|
||||||
*/
|
*/
|
||||||
public void set(final int n, final int value) {
|
public void set(final int n, final int value) {
|
||||||
BigInteger val2 = new BigInteger("" + value);
|
final BigInteger val2 = new BigInteger("" + value);
|
||||||
set(n, val2);
|
set(n, val2);
|
||||||
} /* set */
|
} /* set */
|
||||||
|
|
||||||
@ -210,9 +216,11 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* If the polynomial is identical to 0, 0 is returned.
|
* If the polynomial is identical to 0, 0 is returned.
|
||||||
*/
|
*/
|
||||||
public int ldegree() {
|
public int ldegree() {
|
||||||
for (int n = 0; n < a.size(); n++)
|
for (int n = 0; n < a.size(); n++) {
|
||||||
if (a.elementAt(n).compareTo(BigInteger.ZERO) != 0)
|
if (a.elementAt(n).compareTo(BigInteger.ZERO) != 0) {
|
||||||
return n;
|
return n;
|
||||||
|
}
|
||||||
|
}
|
||||||
return 0;
|
return 0;
|
||||||
} /* ldegree */
|
} /* ldegree */
|
||||||
|
|
||||||
@ -227,10 +235,12 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2010-08-27
|
* @since 2010-08-27
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly multiply(final BigInteger val) {
|
public BigIntegerPoly multiply(final BigInteger val) {
|
||||||
BigIntegerPoly resul = new BigIntegerPoly();
|
final BigIntegerPoly resul = new BigIntegerPoly();
|
||||||
if (val.compareTo(BigInteger.ZERO) != 0)
|
if (val.compareTo(BigInteger.ZERO) != 0) {
|
||||||
for (int n = 0; n < a.size(); n++)
|
for (int n = 0; n < a.size(); n++) {
|
||||||
resul.set(n, a.elementAt(n).multiply(val));
|
resul.set(n, a.elementAt(n).multiply(val));
|
||||||
|
}
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* multiply */
|
} /* multiply */
|
||||||
|
|
||||||
@ -242,15 +252,16 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @return the product of this with the other polynomial
|
* @return the product of this with the other polynomial
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly multiply(final BigIntegerPoly val) {
|
public BigIntegerPoly multiply(final BigIntegerPoly val) {
|
||||||
BigIntegerPoly resul = new BigIntegerPoly();
|
final BigIntegerPoly resul = new BigIntegerPoly();
|
||||||
/*
|
/*
|
||||||
* the degree of the result is the sum of the two degrees.
|
* the degree of the result is the sum of the two degrees.
|
||||||
*/
|
*/
|
||||||
final int nmax = degree() + val.degree();
|
final int nmax = degree() + val.degree();
|
||||||
for (int n = 0; n <= nmax; n++) {
|
for (int n = 0; n <= nmax; n++) {
|
||||||
BigInteger coef = BigInteger.ZERO;
|
BigInteger coef = BigInteger.ZERO;
|
||||||
for (int nleft = 0; nleft <= n; nleft++)
|
for (int nleft = 0; nleft <= n; nleft++) {
|
||||||
coef = coef.add(at(nleft).multiply(val.at(n - nleft)));
|
coef = coef.add(at(nleft).multiply(val.at(n - nleft)));
|
||||||
|
}
|
||||||
resul.set(n, coef);
|
resul.set(n, coef);
|
||||||
}
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
@ -266,11 +277,12 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
*/
|
*/
|
||||||
public BigIntegerPoly pow(final int n) throws ArithmeticException {
|
public BigIntegerPoly pow(final int n) throws ArithmeticException {
|
||||||
BigIntegerPoly resul = new BigIntegerPoly("1");
|
BigIntegerPoly resul = new BigIntegerPoly("1");
|
||||||
if (n < 0)
|
if (n < 0) {
|
||||||
throw new ArithmeticException("negative polynomial power " + n);
|
throw new ArithmeticException("negative polynomial power " + n);
|
||||||
else {
|
} else {
|
||||||
for (int i = 1; i <= n; i++)
|
for (int i = 1; i <= n; i++) {
|
||||||
resul = resul.multiply(this);
|
resul = resul.multiply(this);
|
||||||
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
return resul;
|
return resul;
|
||||||
}
|
}
|
||||||
@ -285,14 +297,14 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2010-08-27
|
* @since 2010-08-27
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly add(final BigIntegerPoly val) {
|
public BigIntegerPoly add(final BigIntegerPoly val) {
|
||||||
BigIntegerPoly resul = new BigIntegerPoly();
|
final BigIntegerPoly resul = new BigIntegerPoly();
|
||||||
/*
|
/*
|
||||||
* the degree of the result is the larger of the two degrees (before
|
* the degree of the result is the larger of the two degrees (before
|
||||||
* simplify() at least).
|
* simplify() at least).
|
||||||
*/
|
*/
|
||||||
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
||||||
for (int n = 0; n <= nmax; n++) {
|
for (int n = 0; n <= nmax; n++) {
|
||||||
BigInteger coef = at(n).add(val.at(n));
|
final BigInteger coef = at(n).add(val.at(n));
|
||||||
resul.set(n, coef);
|
resul.set(n, coef);
|
||||||
}
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
@ -308,14 +320,14 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2008-10-25
|
* @since 2008-10-25
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly subtract(final BigIntegerPoly val) {
|
public BigIntegerPoly subtract(final BigIntegerPoly val) {
|
||||||
BigIntegerPoly resul = new BigIntegerPoly();
|
final BigIntegerPoly resul = new BigIntegerPoly();
|
||||||
/*
|
/*
|
||||||
* the degree of the result is the larger of the two degrees (before
|
* the degree of the result is the larger of the two degrees (before
|
||||||
* simplify() at least).
|
* simplify() at least).
|
||||||
*/
|
*/
|
||||||
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
||||||
for (int n = 0; n <= nmax; n++) {
|
for (int n = 0; n <= nmax; n++) {
|
||||||
BigInteger coef = at(n).subtract(val.at(n));
|
final BigInteger coef = at(n).subtract(val.at(n));
|
||||||
resul.set(n, coef);
|
resul.set(n, coef);
|
||||||
}
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
@ -334,19 +346,20 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2012-03-01
|
* @since 2012-03-01
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly[] divideAndRemainder(final BigIntegerPoly val) {
|
public BigIntegerPoly[] divideAndRemainder(final BigIntegerPoly val) {
|
||||||
BigIntegerPoly[] ret = new BigIntegerPoly[2];
|
final BigIntegerPoly[] ret = new BigIntegerPoly[2];
|
||||||
/*
|
/*
|
||||||
* remove any high-order zeros. note that the clone() operation calls
|
* remove any high-order zeros. note that the clone() operation calls
|
||||||
* simplify().
|
* simplify().
|
||||||
*/
|
*/
|
||||||
BigIntegerPoly valSimpl = val.clone();
|
final BigIntegerPoly valSimpl = val.clone();
|
||||||
BigIntegerPoly thisSimpl = clone();
|
final BigIntegerPoly thisSimpl = clone();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* catch the case with val equal to zero
|
* catch the case with val equal to zero
|
||||||
*/
|
*/
|
||||||
if (valSimpl.degree() == 0 && valSimpl.a.firstElement().compareTo(BigInteger.ZERO) == 0)
|
if (valSimpl.degree() == 0 && valSimpl.a.firstElement().compareTo(BigInteger.ZERO) == 0) {
|
||||||
throw new ArithmeticException("Division through zero polynomial");
|
throw new ArithmeticException("Division through zero polynomial");
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* degree of this smaller than degree of val: remainder is this
|
* degree of this smaller than degree of val: remainder is this
|
||||||
*/
|
*/
|
||||||
@ -363,9 +376,10 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* polynomial division cannot be done with integer coefficients.
|
* polynomial division cannot be done with integer coefficients.
|
||||||
*/
|
*/
|
||||||
ret[0] = new BigIntegerPoly();
|
ret[0] = new BigIntegerPoly();
|
||||||
BigInteger[] newc = thisSimpl.a.lastElement().divideAndRemainder(valSimpl.a.lastElement());
|
final BigInteger[] newc = thisSimpl.a.lastElement().divideAndRemainder(valSimpl.a.lastElement());
|
||||||
if (newc[1].compareTo(BigInteger.ZERO) != 0)
|
if (newc[1].compareTo(BigInteger.ZERO) != 0) {
|
||||||
throw new ArithmeticException("Incompatible leading term in " + this + " / " + val);
|
throw new ArithmeticException("Incompatible leading term in " + this + " / " + val);
|
||||||
|
}
|
||||||
ret[0].set(thisSimpl.degree() - valSimpl.degree(), newc[0]);
|
ret[0].set(thisSimpl.degree() - valSimpl.degree(), newc[0]);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -378,10 +392,10 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
/*
|
/*
|
||||||
* any remainder left ?
|
* any remainder left ?
|
||||||
*/
|
*/
|
||||||
if (ret[1].degree() < valSimpl.degree())
|
if (ret[1].degree() < valSimpl.degree()) {
|
||||||
;
|
;
|
||||||
else {
|
} else {
|
||||||
BigIntegerPoly rem[] = ret[1].divideAndRemainder(val);
|
final BigIntegerPoly rem[] = ret[1].divideAndRemainder(val);
|
||||||
ret[0] = ret[0].add(rem[0]);
|
ret[0] = ret[0].add(rem[0]);
|
||||||
ret[1] = rem[1];
|
ret[1] = rem[1];
|
||||||
}
|
}
|
||||||
@ -399,13 +413,15 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
public String toString() {
|
public String toString() {
|
||||||
String str = new String();
|
String str = new String();
|
||||||
for (int n = 0; n < a.size(); n++) {
|
for (int n = 0; n < a.size(); n++) {
|
||||||
if (n == 0)
|
if (n == 0) {
|
||||||
str += a.elementAt(n).toString();
|
str += a.elementAt(n).toString();
|
||||||
else
|
} else {
|
||||||
str += "," + a.elementAt(n).toString();
|
str += "," + a.elementAt(n).toString();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (str.length() == 0)
|
if (str.length() == 0) {
|
||||||
str = "0";
|
str = "0";
|
||||||
|
}
|
||||||
return str;
|
return str;
|
||||||
} /* toString */
|
} /* toString */
|
||||||
|
|
||||||
@ -422,18 +438,21 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
final BigInteger num = a.elementAt(n);
|
final BigInteger num = a.elementAt(n);
|
||||||
if (num.compareTo(BigInteger.ZERO) != 0) {
|
if (num.compareTo(BigInteger.ZERO) != 0) {
|
||||||
str += " ";
|
str += " ";
|
||||||
if (num.compareTo(BigInteger.ZERO) > 0 && n > 0)
|
if (num.compareTo(BigInteger.ZERO) > 0 && n > 0) {
|
||||||
str += "+";
|
str += "+";
|
||||||
|
}
|
||||||
str += a.elementAt(n).toString();
|
str += a.elementAt(n).toString();
|
||||||
if (n > 0) {
|
if (n > 0) {
|
||||||
str += "*x";
|
str += "*x";
|
||||||
if (n > 1)
|
if (n > 1) {
|
||||||
str += "^" + n;
|
str += "^" + n;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (str.length() == 0)
|
if (str.length() == 0) {
|
||||||
str = "0";
|
str = "0";
|
||||||
|
}
|
||||||
return str;
|
return str;
|
||||||
} /* toPString */
|
} /* toPString */
|
||||||
|
|
||||||
@ -443,12 +462,14 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
*/
|
*/
|
||||||
protected void simplify() {
|
protected void simplify() {
|
||||||
int n = a.size() - 1;
|
int n = a.size() - 1;
|
||||||
if (n >= 0)
|
if (n >= 0) {
|
||||||
while (a.elementAt(n).compareTo(BigInteger.ZERO) == 0) {
|
while (a.elementAt(n).compareTo(BigInteger.ZERO) == 0) {
|
||||||
a.removeElementAt(n);
|
a.removeElementAt(n);
|
||||||
if (--n < 0)
|
if (--n < 0) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} /* simplify */
|
} /* simplify */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -464,7 +485,7 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
*/
|
*/
|
||||||
return new BigIntegerPoly();
|
return new BigIntegerPoly();
|
||||||
} else {
|
} else {
|
||||||
BigIntegerPoly d = new BigIntegerPoly();
|
final BigIntegerPoly d = new BigIntegerPoly();
|
||||||
for (int i = 1; i <= degree(); i++) {
|
for (int i = 1; i <= degree(); i++) {
|
||||||
final BigInteger c = a.elementAt(i).multiply(new BigInteger("" + i));
|
final BigInteger c = a.elementAt(i).multiply(new BigInteger("" + i));
|
||||||
d.set(i - 1, c);
|
d.set(i - 1, c);
|
||||||
@ -480,9 +501,10 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2010-08-27
|
* @since 2010-08-27
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly trunc(int newdeg) {
|
public BigIntegerPoly trunc(int newdeg) {
|
||||||
BigIntegerPoly t = new BigIntegerPoly();
|
final BigIntegerPoly t = new BigIntegerPoly();
|
||||||
for (int i = 0; i <= newdeg; i++)
|
for (int i = 0; i <= newdeg; i++) {
|
||||||
t.set(i, at(i));
|
t.set(i, at(i));
|
||||||
|
}
|
||||||
t.simplify();
|
t.simplify();
|
||||||
return t;
|
return t;
|
||||||
} /* trunc */
|
} /* trunc */
|
||||||
@ -497,14 +519,16 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* @since 2010-08-29
|
* @since 2010-08-29
|
||||||
*/
|
*/
|
||||||
public BigIntegerPoly binomialTInv(int maxdeg) {
|
public BigIntegerPoly binomialTInv(int maxdeg) {
|
||||||
BigIntegerPoly r = new BigIntegerPoly();
|
final BigIntegerPoly r = new BigIntegerPoly();
|
||||||
for (int i = 0; i <= maxdeg; i++) {
|
for (int i = 0; i <= maxdeg; i++) {
|
||||||
BigInteger c = BigInteger.ZERO;
|
BigInteger c = BigInteger.ZERO;
|
||||||
for (int j = 0; j <= i && j < a.size(); j++)
|
for (int j = 0; j <= i && j < a.size(); j++) {
|
||||||
if ((j + i) % 2 != 0)
|
if ((j + i) % 2 != 0) {
|
||||||
c = c.subtract(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
c = c.subtract(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
||||||
else
|
} else {
|
||||||
c = c.add(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
c = c.add(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
||||||
|
}
|
||||||
|
}
|
||||||
r.set(i, c);
|
r.set(i, c);
|
||||||
}
|
}
|
||||||
r.simplify();
|
r.simplify();
|
||||||
@ -537,31 +561,34 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
*/
|
*/
|
||||||
public Vector<BigInteger> iroots() {
|
public Vector<BigInteger> iroots() {
|
||||||
/* The vector of the roots */
|
/* The vector of the roots */
|
||||||
Vector<BigInteger> res = new Vector<>();
|
final Vector<BigInteger> res = new Vector<>();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* collect the zero
|
* collect the zero
|
||||||
*/
|
*/
|
||||||
if (a.firstElement().compareTo(BigInteger.ZERO) == 0)
|
if (a.firstElement().compareTo(BigInteger.ZERO) == 0) {
|
||||||
res.add(BigInteger.ZERO);
|
res.add(BigInteger.ZERO);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* collect the divisors of the constant element (or the reduced
|
* collect the divisors of the constant element (or the reduced
|
||||||
* polynomial)
|
* polynomial)
|
||||||
*/
|
*/
|
||||||
int l = ldegree();
|
final int l = ldegree();
|
||||||
if (a.elementAt(l).compareTo(BigInteger.ZERO) != 0) {
|
if (a.elementAt(l).compareTo(BigInteger.ZERO) != 0) {
|
||||||
Vector<BigInteger> cand = BigIntegerMath.divisors(a.elementAt(l).abs());
|
final Vector<BigInteger> cand = BigIntegerMath.divisors(a.elementAt(l).abs());
|
||||||
|
|
||||||
/* check the divisors (both signs) */
|
/* check the divisors (both signs) */
|
||||||
for (int i = 0; i < cand.size(); i++) {
|
for (int i = 0; i < cand.size(); i++) {
|
||||||
BigInteger roo = valueOf(cand.elementAt(i));
|
BigInteger roo = valueOf(cand.elementAt(i));
|
||||||
if (roo.compareTo(BigInteger.ZERO) == 0)
|
if (roo.compareTo(BigInteger.ZERO) == 0) {
|
||||||
/* found a root cand[i] */
|
/* found a root cand[i] */
|
||||||
res.add(cand.elementAt(i));
|
res.add(cand.elementAt(i));
|
||||||
|
}
|
||||||
roo = valueOf(cand.elementAt(i).negate());
|
roo = valueOf(cand.elementAt(i).negate());
|
||||||
if (roo.compareTo(BigInteger.ZERO) == 0)
|
if (roo.compareTo(BigInteger.ZERO) == 0) {
|
||||||
res.add(cand.elementAt(i).negate());
|
res.add(cand.elementAt(i).negate());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
@ -581,15 +608,16 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
/*
|
/*
|
||||||
* The vector of the factors to be returned
|
* The vector of the factors to be returned
|
||||||
*/
|
*/
|
||||||
Vector<BigIntegerPoly> res = new Vector<>();
|
final Vector<BigIntegerPoly> res = new Vector<>();
|
||||||
|
|
||||||
if (degree() < 2)
|
if (degree() < 2) {
|
||||||
return res;
|
return res;
|
||||||
|
}
|
||||||
|
|
||||||
BigInteger bsco = a.firstElement().abs();
|
final BigInteger bsco = a.firstElement().abs();
|
||||||
Vector<BigInteger> b = BigIntegerMath.divisors(bsco);
|
final Vector<BigInteger> b = BigIntegerMath.divisors(bsco);
|
||||||
BigInteger csco = a.lastElement().abs();
|
final BigInteger csco = a.lastElement().abs();
|
||||||
Vector<BigInteger> c = BigIntegerMath.divisors(csco);
|
final Vector<BigInteger> c = BigIntegerMath.divisors(csco);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Generate the floating point values of roots. To have some reasonable
|
* Generate the floating point values of roots. To have some reasonable
|
||||||
@ -601,8 +629,8 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* estimate
|
* estimate
|
||||||
* and adding 6 safety digits
|
* and adding 6 safety digits
|
||||||
*/
|
*/
|
||||||
RatPoly thisDec = toRatPoly();
|
final RatPoly thisDec = toRatPoly();
|
||||||
Vector<BigComplex> roo = thisDec.roots(6 + (int) (0.3 * bsco.bitCount()));
|
final Vector<BigComplex> roo = thisDec.roots(6 + (int) (0.3 * bsco.bitCount()));
|
||||||
|
|
||||||
final BigDecimal half = new BigDecimal("0.5");
|
final BigDecimal half = new BigDecimal("0.5");
|
||||||
|
|
||||||
@ -613,9 +641,9 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
* coefficient.
|
* coefficient.
|
||||||
* Solve z*(c*z+a)=-b or c*z+a = -b/z or -b/z-c*z = some integer a.
|
* Solve z*(c*z+a)=-b or c*z+a = -b/z or -b/z-c*z = some integer a.
|
||||||
*/
|
*/
|
||||||
for (BigComplex z : roo) {
|
for (final BigComplex z : roo) {
|
||||||
for (BigInteger bco : b)
|
for (final BigInteger bco : b) {
|
||||||
for (BigInteger cco : c) {
|
for (final BigInteger cco : c) {
|
||||||
/*
|
/*
|
||||||
* the major reason to avoid the case b=0 is that this would
|
* the major reason to avoid the case b=0 is that this would
|
||||||
* require precaution of double counting below. Note that
|
* require precaution of double counting below. Note that
|
||||||
@ -624,7 +652,7 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
*/
|
*/
|
||||||
if (bco.signum() != 0) {
|
if (bco.signum() != 0) {
|
||||||
for (int sig = -1; sig <= 1; sig += 2) {
|
for (int sig = -1; sig <= 1; sig += 2) {
|
||||||
BigInteger bcosig = (sig > 0) ? bco : bco.negate();
|
final BigInteger bcosig = (sig > 0) ? bco : bco.negate();
|
||||||
/*
|
/*
|
||||||
* -a = b/z+c*z has real part b*Re(z)/|z|^2+c*Re(z)
|
* -a = b/z+c*z has real part b*Re(z)/|z|^2+c*Re(z)
|
||||||
* = Re z *( b/|z|^2+c)
|
* = Re z *( b/|z|^2+c)
|
||||||
@ -634,22 +662,24 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
/*
|
/*
|
||||||
* convert to a with round-to-nearest
|
* convert to a with round-to-nearest
|
||||||
*/
|
*/
|
||||||
BigInteger a = negA.negate().add(half).toBigInteger();
|
final BigInteger a = negA.negate().add(half).toBigInteger();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* test the polynomial remainder. if zero, add the
|
* test the polynomial remainder. if zero, add the
|
||||||
* term
|
* term
|
||||||
* to the results.
|
* to the results.
|
||||||
*/
|
*/
|
||||||
BigIntegerPoly dtst = new BigIntegerPoly("" + bcosig + "," + a + "," + cco);
|
final BigIntegerPoly dtst = new BigIntegerPoly("" + bcosig + "," + a + "," + cco);
|
||||||
try {
|
try {
|
||||||
BigIntegerPoly[] rm = divideAndRemainder(dtst);
|
final BigIntegerPoly[] rm = divideAndRemainder(dtst);
|
||||||
if (rm[1].isZero())
|
if (rm[1].isZero()) {
|
||||||
res.add(dtst);
|
res.add(dtst);
|
||||||
} catch (ArithmeticException ex) {}
|
}
|
||||||
|
} catch (final ArithmeticException ex) {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return res;
|
return res;
|
||||||
@ -679,16 +709,16 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
/*
|
/*
|
||||||
* this ought be entirely rewritten in terms of the LLL algorithm
|
* this ought be entirely rewritten in terms of the LLL algorithm
|
||||||
*/
|
*/
|
||||||
Vector<BigIntegerPoly> fac = new Vector<>();
|
final Vector<BigIntegerPoly> fac = new Vector<>();
|
||||||
|
|
||||||
/* collect integer roots (polynomial factors of degree 1) */
|
/* collect integer roots (polynomial factors of degree 1) */
|
||||||
Vector<BigInteger> r = iroots();
|
final Vector<BigInteger> r = iroots();
|
||||||
BigIntegerPoly[] res = new BigIntegerPoly[2];
|
BigIntegerPoly[] res = new BigIntegerPoly[2];
|
||||||
res[0] = this;
|
res[0] = this;
|
||||||
for (BigInteger i : r) {
|
for (final BigInteger i : r) {
|
||||||
int deg = rootDeg(i);
|
final int deg = rootDeg(i);
|
||||||
/* construct the factor x-i */
|
/* construct the factor x-i */
|
||||||
BigIntegerPoly f = new BigIntegerPoly("" + i.negate() + ",1");
|
final BigIntegerPoly f = new BigIntegerPoly("" + i.negate() + ",1");
|
||||||
for (int mu = 0; mu < deg; mu++) {
|
for (int mu = 0; mu < deg; mu++) {
|
||||||
fac.add(f);
|
fac.add(f);
|
||||||
res = res[0].divideAndRemainder(f);
|
res = res[0].divideAndRemainder(f);
|
||||||
@ -698,21 +728,22 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
/*
|
/*
|
||||||
* collect factors which are polynomials of degree 2
|
* collect factors which are polynomials of degree 2
|
||||||
*/
|
*/
|
||||||
Vector<BigIntegerPoly> pol2 = i2roots();
|
final Vector<BigIntegerPoly> pol2 = i2roots();
|
||||||
for (BigIntegerPoly i : pol2) {
|
for (final BigIntegerPoly i : pol2) {
|
||||||
/*
|
/*
|
||||||
* the internal loop catches cases with higher
|
* the internal loop catches cases with higher
|
||||||
* powers of individual polynomials (of actual degree 2 or 4...)
|
* powers of individual polynomials (of actual degree 2 or 4...)
|
||||||
*/
|
*/
|
||||||
while (res[0].degree() >= 2) {
|
while (res[0].degree() >= 2) {
|
||||||
try {
|
try {
|
||||||
BigIntegerPoly[] dtst = res[0].divideAndRemainder(i);
|
final BigIntegerPoly[] dtst = res[0].divideAndRemainder(i);
|
||||||
if (dtst[1].isZero()) {
|
if (dtst[1].isZero()) {
|
||||||
fac.add(i);
|
fac.add(i);
|
||||||
res = dtst;
|
res = dtst;
|
||||||
} else
|
} else {
|
||||||
break;
|
break;
|
||||||
} catch (ArithmeticException ex) {
|
}
|
||||||
|
} catch (final ArithmeticException ex) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -721,8 +752,9 @@ public class BigIntegerPoly implements Cloneable {
|
|||||||
/*
|
/*
|
||||||
* add remaining factor, if not equal to 1
|
* add remaining factor, if not equal to 1
|
||||||
*/
|
*/
|
||||||
if (res[0].degree() > 0 || res[0].a.firstElement().compareTo(BigInteger.ONE) != 0)
|
if (res[0].degree() > 0 || res[0].a.firstElement().compareTo(BigInteger.ONE) != 0) {
|
||||||
fac.add(res[0]);
|
fac.add(res[0]);
|
||||||
|
}
|
||||||
return fac;
|
return fac;
|
||||||
} /* ifactor */
|
} /* ifactor */
|
||||||
|
|
||||||
|
@ -60,17 +60,18 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* @since 2011-02-12
|
* @since 2011-02-12
|
||||||
*/
|
*/
|
||||||
public BigSurd(Rational a, Rational b) {
|
public BigSurd(Rational a, Rational b) {
|
||||||
this.pref = a;
|
pref = a;
|
||||||
/*
|
/*
|
||||||
* reject attempts to use a negative b
|
* reject attempts to use a negative b
|
||||||
*/
|
*/
|
||||||
if (b.signum() < 0)
|
if (b.signum() < 0) {
|
||||||
throw new ProviderException("Not implemented: imaginary surds");
|
throw new ProviderException("Not implemented: imaginary surds");
|
||||||
this.disc = b;
|
}
|
||||||
|
disc = b;
|
||||||
try {
|
try {
|
||||||
normalize();
|
normalize();
|
||||||
normalizeG();
|
normalizeG();
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -112,8 +113,8 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public BigSurd clone() {
|
public BigSurd clone() {
|
||||||
Rational fclon = pref.clone();
|
final Rational fclon = pref.clone();
|
||||||
Rational dclon = disc.clone();
|
final Rational dclon = disc.clone();
|
||||||
/*
|
/*
|
||||||
* the main intent here is to bypass any attempt to reduce the
|
* the main intent here is to bypass any attempt to reduce the
|
||||||
* discriminant
|
* discriminant
|
||||||
@ -121,7 +122,7 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* already done
|
* already done
|
||||||
* in the current copy of the number.
|
* in the current copy of the number.
|
||||||
*/
|
*/
|
||||||
BigSurd cl = new BigSurd();
|
final BigSurd cl = new BigSurd();
|
||||||
cl.pref = fclon;
|
cl.pref = fclon;
|
||||||
cl.disc = dclon;
|
cl.disc = dclon;
|
||||||
return cl;
|
return cl;
|
||||||
@ -136,13 +137,14 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
|
|
||||||
public BigSurdVec add(final BigSurd val) {
|
public BigSurdVec add(final BigSurd val) {
|
||||||
// zero plus somethings yields something
|
// zero plus somethings yields something
|
||||||
if (signum() == 0)
|
if (signum() == 0) {
|
||||||
return new BigSurdVec(val);
|
return new BigSurdVec(val);
|
||||||
else if (val.signum() == 0)
|
} else if (val.signum() == 0) {
|
||||||
return new BigSurdVec(this);
|
return new BigSurdVec(this);
|
||||||
else
|
} else {
|
||||||
// let the ctor of BigSurdVec to the work
|
// let the ctor of BigSurdVec to the work
|
||||||
return new BigSurdVec(this, val);
|
return new BigSurdVec(this, val);
|
||||||
|
}
|
||||||
} /* BigSurd.add */
|
} /* BigSurd.add */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -190,7 +192,7 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* @since 2011-02-12
|
* @since 2011-02-12
|
||||||
*/
|
*/
|
||||||
public BigSurd multiply(final int val) {
|
public BigSurd multiply(final int val) {
|
||||||
BigInteger tmp = new BigInteger("" + val);
|
final BigInteger tmp = new BigInteger("" + val);
|
||||||
return multiply(tmp);
|
return multiply(tmp);
|
||||||
} /* BigSurd.multiply */
|
} /* BigSurd.multiply */
|
||||||
|
|
||||||
@ -216,14 +218,15 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* @since 2011-02-12
|
* @since 2011-02-12
|
||||||
*/
|
*/
|
||||||
public BigSurd divide(final BigSurd val) throws Error {
|
public BigSurd divide(final BigSurd val) throws Error {
|
||||||
if (val.signum() == 0)
|
if (val.signum() == 0) {
|
||||||
throw new ArithmeticException("Dividing " + toFancyString() + " through zero.");
|
throw new ArithmeticException("Dividing " + toFancyString() + " through zero.");
|
||||||
|
}
|
||||||
return new BigSurd(pref.divide(val.pref), disc.divide(val.disc));
|
return new BigSurd(pref.divide(val.pref), disc.divide(val.disc));
|
||||||
} /* BigSurd.divide */
|
} /* BigSurd.divide */
|
||||||
|
|
||||||
private String toFancyString() {
|
private String toFancyString() {
|
||||||
BigSurd bs = this;
|
final BigSurd bs = this;
|
||||||
BigInteger denominator = pref.b;
|
final BigInteger denominator = pref.b;
|
||||||
String s = "";
|
String s = "";
|
||||||
if (denominator.compareTo(BigInteger.ONE) != 0) {
|
if (denominator.compareTo(BigInteger.ONE) != 0) {
|
||||||
s += "(";
|
s += "(";
|
||||||
@ -233,7 +236,7 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
} else if (bs.isRational()) {
|
} else if (bs.isRational()) {
|
||||||
s += bs.toRational().toString();
|
s += bs.toRational().toString();
|
||||||
} else {
|
} else {
|
||||||
BigInteger numerator = bs.pref.a;
|
final BigInteger numerator = bs.pref.a;
|
||||||
if (numerator.compareTo(BigInteger.ONE) != 0) {
|
if (numerator.compareTo(BigInteger.ONE) != 0) {
|
||||||
s += numerator.toString();
|
s += numerator.toString();
|
||||||
s += "*";
|
s += "*";
|
||||||
@ -262,8 +265,9 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* @since 2011-02-12
|
* @since 2011-02-12
|
||||||
*/
|
*/
|
||||||
public BigSurd divide(final BigInteger val) throws Error {
|
public BigSurd divide(final BigInteger val) throws Error {
|
||||||
if (val.signum() == 0)
|
if (val.signum() == 0) {
|
||||||
throw new ArithmeticException("Dividing " + toFancyString() + " through zero.");
|
throw new ArithmeticException("Dividing " + toFancyString() + " through zero.");
|
||||||
|
}
|
||||||
return new BigSurd(pref.divide(val), disc);
|
return new BigSurd(pref.divide(val), disc);
|
||||||
} /* BigSurd.divide */
|
} /* BigSurd.divide */
|
||||||
|
|
||||||
@ -277,8 +281,9 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* @since 2011-02-12
|
* @since 2011-02-12
|
||||||
*/
|
*/
|
||||||
public BigSurd divide(int val) throws Error {
|
public BigSurd divide(int val) throws Error {
|
||||||
if (val == 0)
|
if (val == 0) {
|
||||||
throw new ArithmeticException("Dividing " + toFancyString() + " through zero.");
|
throw new ArithmeticException("Dividing " + toFancyString() + " through zero.");
|
||||||
|
}
|
||||||
return new BigSurd(pref.divide(val), disc);
|
return new BigSurd(pref.divide(val), disc);
|
||||||
} /* BigSurd.divide */
|
} /* BigSurd.divide */
|
||||||
|
|
||||||
@ -293,7 +298,7 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* This is trying to be quick, avoiding normalize(), by toggling
|
* This is trying to be quick, avoiding normalize(), by toggling
|
||||||
* the sign in a clone()
|
* the sign in a clone()
|
||||||
*/
|
*/
|
||||||
BigSurd n = clone();
|
final BigSurd n = clone();
|
||||||
n.pref = n.pref.negate();
|
n.pref = n.pref.negate();
|
||||||
return n;
|
return n;
|
||||||
} /* BigSurd.negate */
|
} /* BigSurd.negate */
|
||||||
@ -325,16 +330,21 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
*/
|
*/
|
||||||
final int sig = signum();
|
final int sig = signum();
|
||||||
final int sigv = val.signum();
|
final int sigv = val.signum();
|
||||||
if (sig < 0 && sigv >= 0)
|
if (sig < 0 && sigv >= 0) {
|
||||||
return -1;
|
return -1;
|
||||||
if (sig > 0 && sigv <= 0)
|
}
|
||||||
|
if (sig > 0 && sigv <= 0) {
|
||||||
return 1;
|
return 1;
|
||||||
if (sig == 0 && sigv == 0)
|
}
|
||||||
|
if (sig == 0 && sigv == 0) {
|
||||||
return 0;
|
return 0;
|
||||||
if (sig == 0 && sigv > 0)
|
}
|
||||||
|
if (sig == 0 && sigv > 0) {
|
||||||
return -1;
|
return -1;
|
||||||
if (sig == 0 && sigv < 0)
|
}
|
||||||
|
if (sig == 0 && sigv < 0) {
|
||||||
return 1;
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Work out the cases of equal sign. Compare absolute values by
|
* Work out the cases of equal sign. Compare absolute values by
|
||||||
@ -345,16 +355,13 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
final Rational this2 = sqr();
|
final Rational this2 = sqr();
|
||||||
final Rational val2 = val.sqr();
|
final Rational val2 = val.sqr();
|
||||||
final int c = this2.compareTo(val2);
|
final int c = this2.compareTo(val2);
|
||||||
if (c == 0)
|
if (c == 0) {
|
||||||
return 0;
|
return 0;
|
||||||
/*
|
} else if (sig > 0 && c > 0 || sig < 0 && c < 0) {
|
||||||
* If both values have negative sign, the one with the smaller square is
|
|
||||||
* the larger number.
|
|
||||||
*/
|
|
||||||
else if (sig > 0 && c > 0 || sig < 0 && c < 0)
|
|
||||||
return 1;
|
return 1;
|
||||||
else
|
} else {
|
||||||
return -1;
|
return -1;
|
||||||
|
}
|
||||||
} /* BigSurd.compareTo */
|
} /* BigSurd.compareTo */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -366,10 +373,11 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
if (disc.compareTo(Rational.ONE) != 0 && disc.compareTo(Rational.ZERO) != 0)
|
if (disc.compareTo(Rational.ONE) != 0 && disc.compareTo(Rational.ZERO) != 0) {
|
||||||
return ("(" + pref.toString() + ")*(" + disc.toString() + ")^(1/2)");
|
return ("(" + pref.toString() + ")*(" + disc.toString() + ")^(1/2)");
|
||||||
else
|
} else {
|
||||||
return pref.toString();
|
return pref.toString();
|
||||||
|
}
|
||||||
} /* BigSurd.toString */
|
} /* BigSurd.toString */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -383,9 +391,9 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* First compute the square to prevent overflows if the two pieces of
|
* First compute the square to prevent overflows if the two pieces of
|
||||||
* the prefactor and the discriminant are of very different magnitude.
|
* the prefactor and the discriminant are of very different magnitude.
|
||||||
*/
|
*/
|
||||||
Rational p2 = pref.pow(2).multiply(disc);
|
final Rational p2 = pref.pow(2).multiply(disc);
|
||||||
System.out.println("dv sq " + p2.toString());
|
System.out.println("dv sq " + p2.toString());
|
||||||
double res = p2.doubleValue();
|
final double res = p2.doubleValue();
|
||||||
System.out.println("dv sq " + res);
|
System.out.println("dv sq " + res);
|
||||||
return (pref.signum() >= 0) ? Math.sqrt(res) : -Math.sqrt(res);
|
return (pref.signum() >= 0) ? Math.sqrt(res) : -Math.sqrt(res);
|
||||||
} /* BigSurd.doubleValue */
|
} /* BigSurd.doubleValue */
|
||||||
@ -428,10 +436,11 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
* @since 2012-02-15
|
* @since 2012-02-15
|
||||||
*/
|
*/
|
||||||
public Rational toRational() {
|
public Rational toRational() {
|
||||||
if (isRational())
|
if (isRational()) {
|
||||||
return pref;
|
return pref;
|
||||||
else
|
} else {
|
||||||
throw new ArithmeticException("Undefined conversion " + toFancyString() + " to Rational.");
|
throw new ArithmeticException("Undefined conversion " + toFancyString() + " to Rational.");
|
||||||
|
}
|
||||||
} /* BigSurd.toRational */
|
} /* BigSurd.toRational */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -463,7 +472,7 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
/*
|
/*
|
||||||
* square-free part of the numerator: numer = numC*some^2
|
* square-free part of the numerator: numer = numC*some^2
|
||||||
*/
|
*/
|
||||||
BigInteger numC = BigIntegerMath.core(disc.numer());
|
final BigInteger numC = BigIntegerMath.core(disc.numer());
|
||||||
/*
|
/*
|
||||||
* extract the perfect square of the numerator
|
* extract the perfect square of the numerator
|
||||||
*/
|
*/
|
||||||
@ -478,14 +487,15 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
*/
|
*/
|
||||||
pref = pref.multiply(sqf);
|
pref = pref.multiply(sqf);
|
||||||
|
|
||||||
BigInteger denC = BigIntegerMath.core(disc.denom());
|
final BigInteger denC = BigIntegerMath.core(disc.denom());
|
||||||
sq = disc.denom().divide(denC);
|
sq = disc.denom().divide(denC);
|
||||||
sqf = BigIntegerMath.isqrt(sq);
|
sqf = BigIntegerMath.isqrt(sq);
|
||||||
pref = pref.divide(sqf);
|
pref = pref.divide(sqf);
|
||||||
|
|
||||||
disc = new Rational(numC, denC);
|
disc = new Rational(numC, denC);
|
||||||
} else
|
} else {
|
||||||
pref = Rational.ZERO;
|
pref = Rational.ZERO;
|
||||||
|
}
|
||||||
} /* BigSurd.normalize */
|
} /* BigSurd.normalize */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -544,13 +554,13 @@ public class BigSurd implements Cloneable, Comparable<BigSurd> {
|
|||||||
/*
|
/*
|
||||||
* first the square root of the discriminant
|
* first the square root of the discriminant
|
||||||
*/
|
*/
|
||||||
BigDecimal sqrdis = BigDecimalMath.sqrt(disc.BigDecimalValue(locmc), locmc);
|
final BigDecimal sqrdis = BigDecimalMath.sqrt(disc.BigDecimalValue(locmc), locmc);
|
||||||
/*
|
/*
|
||||||
* Then multiply by the prefactor. If sqrdis is a terminating decimal
|
* Then multiply by the prefactor. If sqrdis is a terminating decimal
|
||||||
* fraction,
|
* fraction,
|
||||||
* we prevent early truncation of the result by truncating later.
|
* we prevent early truncation of the result by truncating later.
|
||||||
*/
|
*/
|
||||||
BigDecimal res = sqrdis.multiply(pref.BigDecimalValue(mc));
|
final BigDecimal res = sqrdis.multiply(pref.BigDecimalValue(mc));
|
||||||
return BigDecimalMath.scalePrec(res, mc);
|
return BigDecimalMath.scalePrec(res, mc);
|
||||||
} /* BigDecimalValue */
|
} /* BigDecimalValue */
|
||||||
|
|
||||||
|
@ -69,7 +69,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
terms.add(b);
|
terms.add(b);
|
||||||
try {
|
try {
|
||||||
normalize();
|
normalize();
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
// TODO Auto-generated catch block
|
// TODO Auto-generated catch block
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
@ -87,16 +87,17 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
/*
|
/*
|
||||||
* nothing to be done if at most one term
|
* nothing to be done if at most one term
|
||||||
*/
|
*/
|
||||||
if (terms.size() <= 1)
|
if (terms.size() <= 1) {
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
Vector<BigSurd> newter = new Vector<>();
|
final Vector<BigSurd> newter = new Vector<>();
|
||||||
newter.add(terms.firstElement());
|
newter.add(terms.firstElement());
|
||||||
/*
|
/*
|
||||||
* add j-th element to the existing vector and combine were possible
|
* add j-th element to the existing vector and combine were possible
|
||||||
*/
|
*/
|
||||||
for (int j = 1; j < terms.size(); j++) {
|
for (int j = 1; j < terms.size(); j++) {
|
||||||
BigSurd todo = terms.elementAt(j);
|
final BigSurd todo = terms.elementAt(j);
|
||||||
boolean merged = false;
|
boolean merged = false;
|
||||||
for (int ex = 0; ex < newter.size(); ex++) {
|
for (int ex = 0; ex < newter.size(); ex++) {
|
||||||
BigSurd v = newter.elementAt(ex);
|
BigSurd v = newter.elementAt(ex);
|
||||||
@ -105,16 +106,16 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* rational number is needed. Replaces v with v+todo = v*(1+r)
|
* rational number is needed. Replaces v with v+todo = v*(1+r)
|
||||||
* if this reduction works.
|
* if this reduction works.
|
||||||
*/
|
*/
|
||||||
BigSurd r = todo.divide(v);
|
final BigSurd r = todo.divide(v);
|
||||||
if (r.isRational()) {
|
if (r.isRational()) {
|
||||||
/* compute r+1 */
|
/* compute r+1 */
|
||||||
Rational newpref = r.toRational().add(1);
|
final Rational newpref = r.toRational().add(1);
|
||||||
/*
|
/*
|
||||||
* eliminate accidental zeros; overwrite with v*(1+r).
|
* eliminate accidental zeros; overwrite with v*(1+r).
|
||||||
*/
|
*/
|
||||||
if (newpref.compareTo(Rational.ZERO) == 0)
|
if (newpref.compareTo(Rational.ZERO) == 0) {
|
||||||
newter.removeElementAt(ex);
|
newter.removeElementAt(ex);
|
||||||
else {
|
} else {
|
||||||
v = v.multiply(newpref);
|
v = v.multiply(newpref);
|
||||||
newter.setElementAt(v, ex);
|
newter.setElementAt(v, ex);
|
||||||
}
|
}
|
||||||
@ -125,8 +126,9 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
/*
|
/*
|
||||||
* append if none of the existing elements matched
|
* append if none of the existing elements matched
|
||||||
*/
|
*/
|
||||||
if (!merged)
|
if (!merged) {
|
||||||
newter.add(todo);
|
newter.add(todo);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* overwrite old version */
|
/* overwrite old version */
|
||||||
@ -148,7 +150,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
try {
|
try {
|
||||||
diff = this.subtract(oth);
|
diff = this.subtract(oth);
|
||||||
return diff.signum();
|
return diff.signum();
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
// TODO Auto-generated catch block
|
// TODO Auto-generated catch block
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
return 0;
|
return 0;
|
||||||
@ -168,34 +170,40 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* the case of zero is unique, because no (reduced) vector of surds
|
* the case of zero is unique, because no (reduced) vector of surds
|
||||||
* other than the one element 0 itself can add/subtract to zero.
|
* other than the one element 0 itself can add/subtract to zero.
|
||||||
*/
|
*/
|
||||||
if (terms.size() == 0)
|
if (terms.size() == 0) {
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* if there is one term: forward to the signum function of BigSurd
|
* if there is one term: forward to the signum function of BigSurd
|
||||||
*/
|
*/
|
||||||
if (terms.size() == 1)
|
if (terms.size() == 1) {
|
||||||
return terms.firstElement().signum();
|
return terms.firstElement().signum();
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* if all terms have a common sign: take that one offsig is the index of
|
* if all terms have a common sign: take that one offsig is the index of
|
||||||
* the first "offending" term in the sense that its sign doese not agree
|
* the first "offending" term in the sense that its sign doese not agree
|
||||||
* with the term[0].
|
* with the term[0].
|
||||||
*/
|
*/
|
||||||
int sig0 = terms.elementAt(0).signum();
|
final int sig0 = terms.elementAt(0).signum();
|
||||||
int offsig = 1;
|
int offsig = 1;
|
||||||
for (; offsig < terms.size(); offsig++)
|
for (; offsig < terms.size(); offsig++) {
|
||||||
if (terms.elementAt(offsig).signum() != sig0)
|
if (terms.elementAt(offsig).signum() != sig0) {
|
||||||
break;
|
break;
|
||||||
if (offsig >= terms.size())
|
}
|
||||||
|
}
|
||||||
|
if (offsig >= terms.size()) {
|
||||||
return sig0;
|
return sig0;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* if there are two terms (now known to have different sign): forward to
|
* if there are two terms (now known to have different sign): forward to
|
||||||
* the comparison of the two elements as BigSurds
|
* the comparison of the two elements as BigSurds
|
||||||
*/
|
*/
|
||||||
if (terms.size() == 2)
|
if (terms.size() == 2) {
|
||||||
return terms.elementAt(0).compareTo(terms.elementAt(1).negate());
|
return terms.elementAt(0).compareTo(terms.elementAt(1).negate());
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* if there are three terms, move the one with the offending sign to the
|
* if there are three terms, move the one with the offending sign to the
|
||||||
@ -206,10 +214,11 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*/
|
*/
|
||||||
if (terms.size() == 3) {
|
if (terms.size() == 3) {
|
||||||
BigSurdVec lhs;
|
BigSurdVec lhs;
|
||||||
if (offsig == 2)
|
if (offsig == 2) {
|
||||||
lhs = new BigSurdVec(terms.elementAt(0), terms.elementAt(1));
|
lhs = new BigSurdVec(terms.elementAt(0), terms.elementAt(1));
|
||||||
else
|
} else {
|
||||||
lhs = new BigSurdVec(terms.elementAt(0), terms.elementAt(2));
|
lhs = new BigSurdVec(terms.elementAt(0), terms.elementAt(2));
|
||||||
|
}
|
||||||
lhs = lhs.sqr();
|
lhs = lhs.sqr();
|
||||||
/*
|
/*
|
||||||
* Strange line: this line isn't used, but it's present in this
|
* Strange line: this line isn't used, but it's present in this
|
||||||
@ -223,13 +232,14 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*
|
*
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
if (lhs.compareTo(lhs) > 0)
|
if (lhs.compareTo(lhs) > 0) {
|
||||||
/*
|
/*
|
||||||
* dominating sign was t(0)+t(offbar)
|
* dominating sign was t(0)+t(offbar)
|
||||||
*/
|
*/
|
||||||
return terms.elementAt(0).signum();
|
return terms.elementAt(0).signum();
|
||||||
else
|
} else {
|
||||||
return terms.elementAt(offsig).signum();
|
return terms.elementAt(offsig).signum();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -252,9 +262,9 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
/*
|
/*
|
||||||
* simple cases with one term forwarded to the BigSurd class
|
* simple cases with one term forwarded to the BigSurd class
|
||||||
*/
|
*/
|
||||||
if (terms.size() == 0)
|
if (terms.size() == 0) {
|
||||||
return BigDecimal.ZERO;
|
return BigDecimal.ZERO;
|
||||||
else if (terms.size() == 1) {
|
} else if (terms.size() == 1) {
|
||||||
return terms.firstElement().BigDecimalValue(mc);
|
return terms.firstElement().BigDecimalValue(mc);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -263,18 +273,20 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* until we are stable to the required result. Keep the old (less
|
* until we are stable to the required result. Keep the old (less
|
||||||
* precise) estimate in res[0], and the newer, more precise in res[1].
|
* precise) estimate in res[0], and the newer, more precise in res[1].
|
||||||
*/
|
*/
|
||||||
BigDecimal[] res = new BigDecimal[2];
|
final BigDecimal[] res = new BigDecimal[2];
|
||||||
res[0] = BigDecimal.ZERO;
|
res[0] = BigDecimal.ZERO;
|
||||||
for (int addpr = 1;; addpr += 3) {
|
for (int addpr = 1;; addpr += 3) {
|
||||||
MathContext locmc = new MathContext(mc.getPrecision() + addpr, mc.getRoundingMode());
|
final MathContext locmc = new MathContext(mc.getPrecision() + addpr, mc.getRoundingMode());
|
||||||
res[1] = BigDecimal.ZERO;
|
res[1] = BigDecimal.ZERO;
|
||||||
for (BigSurd j : terms)
|
for (final BigSurd j : terms) {
|
||||||
res[1] = BigDecimalMath.addRound(res[1], j.BigDecimalValue(locmc));
|
res[1] = BigDecimalMath.addRound(res[1], j.BigDecimalValue(locmc));
|
||||||
|
}
|
||||||
if (addpr > 1) {
|
if (addpr > 1) {
|
||||||
BigDecimal err = res[1].subtract(res[0]).abs();
|
final BigDecimal err = res[1].subtract(res[0]).abs();
|
||||||
int prec = BigDecimalMath.err2prec(res[1], err);
|
final int prec = BigDecimalMath.err2prec(res[1], err);
|
||||||
if (prec > mc.getPrecision())
|
if (prec > mc.getPrecision()) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
res[0] = res[1];
|
res[0] = res[1];
|
||||||
}
|
}
|
||||||
@ -288,7 +300,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @return A truncated version with the precision described by mc
|
* @return A truncated version with the precision described by mc
|
||||||
*/
|
*/
|
||||||
public double doubleValue() {
|
public double doubleValue() {
|
||||||
BigDecimal bd = BigDecimalValue(MathContext.DECIMAL128);
|
final BigDecimal bd = BigDecimalValue(MathContext.DECIMAL128);
|
||||||
return bd.doubleValue();
|
return bd.doubleValue();
|
||||||
} /* doubleValue */
|
} /* doubleValue */
|
||||||
|
|
||||||
@ -298,7 +310,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @return A truncated version with the precision described by mc
|
* @return A truncated version with the precision described by mc
|
||||||
*/
|
*/
|
||||||
public double floatValue() {
|
public double floatValue() {
|
||||||
BigDecimal bd = BigDecimalValue(MathContext.DECIMAL64);
|
final BigDecimal bd = BigDecimalValue(MathContext.DECIMAL64);
|
||||||
return bd.floatValue();
|
return bd.floatValue();
|
||||||
} /* floatValue */
|
} /* floatValue */
|
||||||
|
|
||||||
@ -311,16 +323,16 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public BigSurdVec add(final BigSurdVec val) throws Error {
|
public BigSurdVec add(final BigSurdVec val) throws Error {
|
||||||
BigSurdVec sum = new BigSurdVec();
|
final BigSurdVec sum = new BigSurdVec();
|
||||||
/*
|
/*
|
||||||
* concatenate the vectors and eliminate common overlaps
|
* concatenate the vectors and eliminate common overlaps
|
||||||
*/
|
*/
|
||||||
for (BigSurd term : terms) {
|
for (final BigSurd term : terms) {
|
||||||
if (term.compareTo(BigSurd.ZERO) != 0) {
|
if (term.compareTo(BigSurd.ZERO) != 0) {
|
||||||
sum.terms.add(term);
|
sum.terms.add(term);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (BigSurd term : val.terms) {
|
for (final BigSurd term : val.terms) {
|
||||||
if (term.compareTo(BigSurd.ZERO) != 0) {
|
if (term.compareTo(BigSurd.ZERO) != 0) {
|
||||||
sum.terms.add(term);
|
sum.terms.add(term);
|
||||||
}
|
}
|
||||||
@ -338,7 +350,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public BigSurdVec add(final BigSurd val) throws Error {
|
public BigSurdVec add(final BigSurd val) throws Error {
|
||||||
BigSurdVec sum = new BigSurdVec();
|
final BigSurdVec sum = new BigSurdVec();
|
||||||
/*
|
/*
|
||||||
* concatenate the vectors and eliminate common overlaps
|
* concatenate the vectors and eliminate common overlaps
|
||||||
*/
|
*/
|
||||||
@ -357,13 +369,14 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public BigSurdVec subtract(final BigSurdVec val) throws Error {
|
public BigSurdVec subtract(final BigSurdVec val) throws Error {
|
||||||
BigSurdVec sum = new BigSurdVec();
|
final BigSurdVec sum = new BigSurdVec();
|
||||||
/*
|
/*
|
||||||
* concatenate the vectors and eliminate common overlaps
|
* concatenate the vectors and eliminate common overlaps
|
||||||
*/
|
*/
|
||||||
sum.terms.addAll(terms);
|
sum.terms.addAll(terms);
|
||||||
for (BigSurd s : val.terms)
|
for (final BigSurd s : val.terms) {
|
||||||
sum.terms.add(s.negate());
|
sum.terms.add(s.negate());
|
||||||
|
}
|
||||||
sum.normalize();
|
sum.normalize();
|
||||||
return sum;
|
return sum;
|
||||||
} /* subtract */
|
} /* subtract */
|
||||||
@ -377,7 +390,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public BigSurdVec subtract(final BigSurd val) throws Error {
|
public BigSurdVec subtract(final BigSurd val) throws Error {
|
||||||
BigSurdVec sum = new BigSurdVec();
|
final BigSurdVec sum = new BigSurdVec();
|
||||||
/*
|
/*
|
||||||
* concatenate the vectors and eliminate common overlaps
|
* concatenate the vectors and eliminate common overlaps
|
||||||
*/
|
*/
|
||||||
@ -397,9 +410,10 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
/*
|
/*
|
||||||
* accumulate the negated elements of term one by one
|
* accumulate the negated elements of term one by one
|
||||||
*/
|
*/
|
||||||
BigSurdVec resul = new BigSurdVec();
|
final BigSurdVec resul = new BigSurdVec();
|
||||||
for (BigSurd s : terms)
|
for (final BigSurd s : terms) {
|
||||||
resul.terms.add(s.negate());
|
resul.terms.add(s.negate());
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* no normalization step here, because the negation of all terms does
|
* no normalization step here, because the negation of all terms does
|
||||||
* not introduce new common factors
|
* not introduce new common factors
|
||||||
@ -419,12 +433,15 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* Binomial expansion. First the sum of the terms squared, then 2 times
|
* Binomial expansion. First the sum of the terms squared, then 2 times
|
||||||
* the mixed products.
|
* the mixed products.
|
||||||
*/
|
*/
|
||||||
BigSurdVec resul = new BigSurdVec();
|
final BigSurdVec resul = new BigSurdVec();
|
||||||
for (int i = 0; i < terms.size(); i++)
|
for (int i = 0; i < terms.size(); i++) {
|
||||||
resul.terms.add(new BigSurd(terms.elementAt(i).sqr(), Rational.ONE));
|
resul.terms.add(new BigSurd(terms.elementAt(i).sqr(), Rational.ONE));
|
||||||
for (int i = 0; i < terms.size() - 1; i++)
|
}
|
||||||
for (int j = i + 1; j < terms.size(); j++)
|
for (int i = 0; i < terms.size() - 1; i++) {
|
||||||
|
for (int j = i + 1; j < terms.size(); j++) {
|
||||||
resul.terms.add(terms.elementAt(i).multiply(terms.elementAt(j)).multiply(2));
|
resul.terms.add(terms.elementAt(i).multiply(terms.elementAt(j)).multiply(2));
|
||||||
|
}
|
||||||
|
}
|
||||||
resul.normalize();
|
resul.normalize();
|
||||||
return resul;
|
return resul;
|
||||||
} /* sqr */
|
} /* sqr */
|
||||||
@ -439,28 +456,30 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
* @since 2011-02-12
|
* @since 2011-02-12
|
||||||
*/
|
*/
|
||||||
public BigSurdVec multiply(final BigSurd val) throws Error {
|
public BigSurdVec multiply(final BigSurd val) throws Error {
|
||||||
BigSurdVec resul = new BigSurdVec();
|
final BigSurdVec resul = new BigSurdVec();
|
||||||
for (BigSurd s : terms)
|
for (final BigSurd s : terms) {
|
||||||
resul.terms.add(s.multiply(val));
|
resul.terms.add(s.multiply(val));
|
||||||
|
}
|
||||||
resul.normalize();
|
resul.normalize();
|
||||||
return resul;
|
return resul;
|
||||||
} /* multiply */
|
} /* multiply */
|
||||||
|
|
||||||
public BigSurdVec multiply(final BigSurdVec val) throws Error {
|
public BigSurdVec multiply(final BigSurdVec val) throws Error {
|
||||||
BigSurdVec resul = new BigSurdVec();
|
BigSurdVec resul = new BigSurdVec();
|
||||||
for (BigSurd s : terms) {
|
for (final BigSurd s : terms) {
|
||||||
resul.terms.add(s);
|
resul.terms.add(s);
|
||||||
}
|
}
|
||||||
for (BigSurd s : val.terms) {
|
for (final BigSurd s : val.terms) {
|
||||||
resul = resul.multiply(s);
|
resul = resul.multiply(s);
|
||||||
}
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* multiply */
|
} /* multiply */
|
||||||
|
|
||||||
public BigSurdVec divide(final BigSurd val) throws Error {
|
public BigSurdVec divide(final BigSurd val) throws Error {
|
||||||
BigSurdVec resul = new BigSurdVec();
|
final BigSurdVec resul = new BigSurdVec();
|
||||||
for (BigSurd s : terms)
|
for (final BigSurd s : terms) {
|
||||||
resul.terms.add(s.divide(val));
|
resul.terms.add(s.divide(val));
|
||||||
|
}
|
||||||
resul.normalize();
|
resul.normalize();
|
||||||
return resul;
|
return resul;
|
||||||
} /* multiply */
|
} /* multiply */
|
||||||
@ -468,7 +487,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
public BigSurdVec divide(final BigSurdVec val) throws Error {
|
public BigSurdVec divide(final BigSurdVec val) throws Error {
|
||||||
BigSurdVec resul = new BigSurdVec();
|
BigSurdVec resul = new BigSurdVec();
|
||||||
resul.terms = terms;
|
resul.terms = terms;
|
||||||
for (BigSurd s : val.terms) {
|
for (final BigSurd s : val.terms) {
|
||||||
resul = resul.divide(s);
|
resul = resul.divide(s);
|
||||||
}
|
}
|
||||||
return resul;
|
return resul;
|
||||||
@ -482,7 +501,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*/
|
*/
|
||||||
public boolean isRational() {
|
public boolean isRational() {
|
||||||
boolean val = false;
|
boolean val = false;
|
||||||
for (BigSurd s : terms) {
|
for (final BigSurd s : terms) {
|
||||||
val = s.isRational();
|
val = s.isRational();
|
||||||
if (val == false) {
|
if (val == false) {
|
||||||
break;
|
break;
|
||||||
@ -499,7 +518,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*/
|
*/
|
||||||
public boolean isBigInteger() {
|
public boolean isBigInteger() {
|
||||||
boolean val = false;
|
boolean val = false;
|
||||||
for (BigSurd s : terms) {
|
for (final BigSurd s : terms) {
|
||||||
val = s.isBigInteger();
|
val = s.isBigInteger();
|
||||||
if (val == false) {
|
if (val == false) {
|
||||||
break;
|
break;
|
||||||
@ -515,9 +534,10 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*/
|
*/
|
||||||
public Rational toRational() {
|
public Rational toRational() {
|
||||||
Rational rat = Rational.ZERO;
|
Rational rat = Rational.ZERO;
|
||||||
if (isRational() == false)
|
if (isRational() == false) {
|
||||||
throw new ArithmeticException("Undefined conversion " + toString() + " to Rational.");
|
throw new ArithmeticException("Undefined conversion " + toString() + " to Rational.");
|
||||||
for (BigSurd s : terms) {
|
}
|
||||||
|
for (final BigSurd s : terms) {
|
||||||
rat = rat.add(s.pref);
|
rat = rat.add(s.pref);
|
||||||
}
|
}
|
||||||
return rat;
|
return rat;
|
||||||
@ -530,9 +550,10 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*/
|
*/
|
||||||
public BigInteger toBigInteger() {
|
public BigInteger toBigInteger() {
|
||||||
BigDecimal tmp = BigDecimal.ZERO.setScale(Utils.scale, Utils.scaleMode);
|
BigDecimal tmp = BigDecimal.ZERO.setScale(Utils.scale, Utils.scaleMode);
|
||||||
if (isBigInteger() == false)
|
if (isBigInteger() == false) {
|
||||||
throw new ArithmeticException("Undefined conversion " + toString() + " to Rational.");
|
throw new ArithmeticException("Undefined conversion " + toString() + " to Rational.");
|
||||||
for (BigSurd s : terms) {
|
}
|
||||||
|
for (final BigSurd s : terms) {
|
||||||
tmp = BigDecimalMath.addRound(tmp, s.pref.BigDecimalValue(new MathContext(Utils.scale, Utils.scaleMode2)));
|
tmp = BigDecimalMath.addRound(tmp, s.pref.BigDecimalValue(new MathContext(Utils.scale, Utils.scaleMode2)));
|
||||||
}
|
}
|
||||||
return tmp.toBigInteger();
|
return tmp.toBigInteger();
|
||||||
@ -545,7 +566,7 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
*/
|
*/
|
||||||
public BigDecimal toBigDecimal() {
|
public BigDecimal toBigDecimal() {
|
||||||
BigDecimal tmp = BigDecimal.ZERO.setScale(Utils.scale, Utils.scaleMode);
|
BigDecimal tmp = BigDecimal.ZERO.setScale(Utils.scale, Utils.scaleMode);
|
||||||
for (BigSurd s : terms) {
|
for (final BigSurd s : terms) {
|
||||||
tmp = BigDecimalMath.addRound(tmp, s.BigDecimalValue(new MathContext(Utils.scale, Utils.scaleMode2)));
|
tmp = BigDecimalMath.addRound(tmp, s.BigDecimalValue(new MathContext(Utils.scale, Utils.scaleMode2)));
|
||||||
}
|
}
|
||||||
return tmp;
|
return tmp;
|
||||||
@ -563,14 +584,15 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
/*
|
/*
|
||||||
* simple cases with one term forwarded to the BigSurd class
|
* simple cases with one term forwarded to the BigSurd class
|
||||||
*/
|
*/
|
||||||
if (terms.size() == 0)
|
if (terms.size() == 0) {
|
||||||
return new String("0");
|
return new String("0");
|
||||||
else {
|
} else {
|
||||||
String s = new String();
|
String s = new String();
|
||||||
for (int t = 0; t < terms.size(); t++) {
|
for (int t = 0; t < terms.size(); t++) {
|
||||||
BigSurd bs = terms.elementAt(t);
|
final BigSurd bs = terms.elementAt(t);
|
||||||
if (bs.signum() > 0)
|
if (bs.signum() > 0) {
|
||||||
s += "+";
|
s += "+";
|
||||||
|
}
|
||||||
s += bs.toString();
|
s += bs.toString();
|
||||||
}
|
}
|
||||||
return s;
|
return s;
|
||||||
@ -578,9 +600,9 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
} /* toString */
|
} /* toString */
|
||||||
|
|
||||||
public String toFancyString() {
|
public String toFancyString() {
|
||||||
if (terms.size() == 0)
|
if (terms.size() == 0) {
|
||||||
return new String("0");
|
return new String("0");
|
||||||
else {
|
} else {
|
||||||
BigInteger denominator = BigInteger.ONE;
|
BigInteger denominator = BigInteger.ONE;
|
||||||
for (int i = 0; i < terms.size(); i++) {
|
for (int i = 0; i < terms.size(); i++) {
|
||||||
denominator = denominator.multiply(terms.elementAt(i).pref.b);
|
denominator = denominator.multiply(terms.elementAt(i).pref.b);
|
||||||
@ -590,15 +612,16 @@ public class BigSurdVec implements Comparable<BigSurdVec> {
|
|||||||
s += "(";
|
s += "(";
|
||||||
}
|
}
|
||||||
for (int t = 0; t < terms.size(); t++) {
|
for (int t = 0; t < terms.size(); t++) {
|
||||||
BigSurd bs = terms.elementAt(t);
|
final BigSurd bs = terms.elementAt(t);
|
||||||
if (bs.signum() > 0 && t > 0)
|
if (bs.signum() > 0 && t > 0) {
|
||||||
s += "+";
|
s += "+";
|
||||||
|
}
|
||||||
if (bs.isBigInteger()) {
|
if (bs.isBigInteger()) {
|
||||||
s += bs.BigDecimalValue(new MathContext(Utils.scale, Utils.scaleMode2)).toBigInteger().toString();
|
s += bs.BigDecimalValue(new MathContext(Utils.scale, Utils.scaleMode2)).toBigInteger().toString();
|
||||||
} else if (bs.isRational()) {
|
} else if (bs.isRational()) {
|
||||||
s += bs.toRational().toString();
|
s += bs.toRational().toString();
|
||||||
} else {
|
} else {
|
||||||
BigInteger numerator = bs.pref.multiply(denominator).numer();
|
final BigInteger numerator = bs.pref.multiply(denominator).numer();
|
||||||
if (numerator.compareTo(BigInteger.ONE) != 0) {
|
if (numerator.compareTo(BigInteger.ONE) != 0) {
|
||||||
s += numerator.toString();
|
s += numerator.toString();
|
||||||
s += "*";
|
s += "*";
|
||||||
|
@ -38,20 +38,22 @@ public class Euler {
|
|||||||
while (n >= a.size()) {
|
while (n >= a.size()) {
|
||||||
BigInteger val = BigInteger.ZERO;
|
BigInteger val = BigInteger.ZERO;
|
||||||
boolean sigPos = true;
|
boolean sigPos = true;
|
||||||
int thisn = a.size();
|
final int thisn = a.size();
|
||||||
for (int i = thisn - 1; i > 0; i--) {
|
for (int i = thisn - 1; i > 0; i--) {
|
||||||
BigInteger f = new BigInteger("" + a.elementAt(i).toString());
|
BigInteger f = new BigInteger("" + a.elementAt(i).toString());
|
||||||
f = f.multiply(BigIntegerMath.binomial(2 * thisn, 2 * i));
|
f = f.multiply(BigIntegerMath.binomial(2 * thisn, 2 * i));
|
||||||
if (sigPos)
|
if (sigPos) {
|
||||||
val = val.add(f);
|
val = val.add(f);
|
||||||
else
|
} else {
|
||||||
val = val.subtract(f);
|
val = val.subtract(f);
|
||||||
|
}
|
||||||
sigPos = !sigPos;
|
sigPos = !sigPos;
|
||||||
}
|
}
|
||||||
if (thisn % 2 == 0)
|
if (thisn % 2 == 0) {
|
||||||
val = val.subtract(BigInteger.ONE);
|
val = val.subtract(BigInteger.ONE);
|
||||||
else
|
} else {
|
||||||
val = val.add(BigInteger.ONE);
|
val = val.add(BigInteger.ONE);
|
||||||
|
}
|
||||||
a.add(val);
|
a.add(val);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -36,16 +36,18 @@ public class EulerPhi {
|
|||||||
* @return phi(n)
|
* @return phi(n)
|
||||||
*/
|
*/
|
||||||
public BigInteger at(BigInteger n) {
|
public BigInteger at(BigInteger n) {
|
||||||
if (n.compareTo(BigInteger.ZERO) <= 0)
|
if (n.compareTo(BigInteger.ZERO) <= 0) {
|
||||||
throw new ArithmeticException("negative argument " + n + " of EulerPhi");
|
throw new ArithmeticException("negative argument " + n + " of EulerPhi");
|
||||||
Ifactor prFact = new Ifactor(n);
|
}
|
||||||
|
final Ifactor prFact = new Ifactor(n);
|
||||||
BigInteger phi = n;
|
BigInteger phi = n;
|
||||||
if (n.compareTo(BigInteger.ONE) > 0)
|
if (n.compareTo(BigInteger.ONE) > 0) {
|
||||||
for (int i = 0; i < prFact.primeexp.size(); i += 2) {
|
for (int i = 0; i < prFact.primeexp.size(); i += 2) {
|
||||||
BigInteger p = new BigInteger(prFact.primeexp.elementAt(i).toString());
|
final BigInteger p = new BigInteger(prFact.primeexp.elementAt(i).toString());
|
||||||
BigInteger p_1 = p.subtract(BigInteger.ONE);
|
final BigInteger p_1 = p.subtract(BigInteger.ONE);
|
||||||
phi = phi.multiply(p_1).divide(p);
|
phi = phi.multiply(p_1).divide(p);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
return phi;
|
return phi;
|
||||||
} /* at */
|
} /* at */
|
||||||
|
|
||||||
@ -57,8 +59,8 @@ public class EulerPhi {
|
|||||||
* @since 2006-08-14
|
* @since 2006-08-14
|
||||||
*/
|
*/
|
||||||
public static void main(String[] args) throws ArithmeticException {
|
public static void main(String[] args) throws ArithmeticException {
|
||||||
EulerPhi a = new EulerPhi();
|
final EulerPhi a = new EulerPhi();
|
||||||
int n = (new Integer(args[0])).intValue();
|
final int n = (new Integer(args[0])).intValue();
|
||||||
System.out.println("phi(" + n + ") = " + a.at(n));
|
System.out.println("phi(" + n + ") = " + a.at(n));
|
||||||
}
|
}
|
||||||
} /* EulerPhi */
|
} /* EulerPhi */
|
||||||
|
@ -23,9 +23,9 @@ public class Harmonic {
|
|||||||
* For values of n less than 1, zero is returned.
|
* For values of n less than 1, zero is returned.
|
||||||
*/
|
*/
|
||||||
public Rational at(int n) {
|
public Rational at(int n) {
|
||||||
if (n < 1)
|
if (n < 1) {
|
||||||
return (new Rational(0, 1));
|
return (new Rational(0, 1));
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* start with 1 as the result
|
* start with 1 as the result
|
||||||
*/
|
*/
|
||||||
@ -34,8 +34,9 @@ public class Harmonic {
|
|||||||
/*
|
/*
|
||||||
* add 1/i for i=2..n
|
* add 1/i for i=2..n
|
||||||
*/
|
*/
|
||||||
for (int i = 2; i <= n; i++)
|
for (int i = 2; i <= n; i++) {
|
||||||
a = a.add(new Rational(1, i));
|
a = a.add(new Rational(1, i));
|
||||||
|
}
|
||||||
return a;
|
return a;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -48,7 +48,7 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
primeexp = new Vector<>();
|
primeexp = new Vector<>();
|
||||||
if (number > 1) {
|
if (number > 1) {
|
||||||
int primindx = 0;
|
int primindx = 0;
|
||||||
Prime primes = new Prime();
|
final Prime primes = new Prime();
|
||||||
/*
|
/*
|
||||||
* Test division against all primes.
|
* Test division against all primes.
|
||||||
*/
|
*/
|
||||||
@ -57,12 +57,13 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
/*
|
/*
|
||||||
* primindx=0 refers to 2, =1 to 3, =2 to 5, =3 to 7 etc
|
* primindx=0 refers to 2, =1 to 3, =2 to 5, =3 to 7 etc
|
||||||
*/
|
*/
|
||||||
int p = primes.at(primindx).intValue();
|
final int p = primes.at(primindx).intValue();
|
||||||
while (number % p == 0) {
|
while (number % p == 0) {
|
||||||
ex++;
|
ex++;
|
||||||
number /= p;
|
number /= p;
|
||||||
if (number == 1)
|
if (number == 1) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (ex > 0) {
|
if (ex > 0) {
|
||||||
primeexp.add(new Integer(p));
|
primeexp.add(new Integer(p));
|
||||||
@ -92,18 +93,19 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
primeexp.add(new Integer(0));
|
primeexp.add(new Integer(0));
|
||||||
} else {
|
} else {
|
||||||
int primindx = 0;
|
int primindx = 0;
|
||||||
Prime primes = new Prime();
|
final Prime primes = new Prime();
|
||||||
/*
|
/*
|
||||||
* Test for division against all primes.
|
* Test for division against all primes.
|
||||||
*/
|
*/
|
||||||
while (number.compareTo(BigInteger.ONE) == 1) {
|
while (number.compareTo(BigInteger.ONE) == 1) {
|
||||||
int ex = 0;
|
int ex = 0;
|
||||||
BigInteger p = primes.at(primindx);
|
final BigInteger p = primes.at(primindx);
|
||||||
while (number.remainder(p).compareTo(BigInteger.ZERO) == 0) {
|
while (number.remainder(p).compareTo(BigInteger.ZERO) == 0) {
|
||||||
ex++;
|
ex++;
|
||||||
number = number.divide(p);
|
number = number.divide(p);
|
||||||
if (number.compareTo(BigInteger.ONE) == 0)
|
if (number.compareTo(BigInteger.ONE) == 0) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (ex > 0) {
|
if (ex > 0) {
|
||||||
primeexp.add(new Integer(p.intValue()));
|
primeexp.add(new Integer(p.intValue()));
|
||||||
@ -128,19 +130,20 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
primeexp = new Vector<>(2 * pows.size());
|
primeexp = new Vector<>(2 * pows.size());
|
||||||
if (pows.size() > 0) {
|
if (pows.size() > 0) {
|
||||||
n = BigInteger.ONE;
|
n = BigInteger.ONE;
|
||||||
Prime primes = new Prime();
|
final Prime primes = new Prime();
|
||||||
/*
|
/*
|
||||||
* Build the full number by the product of all powers of the primes.
|
* Build the full number by the product of all powers of the primes.
|
||||||
*/
|
*/
|
||||||
for (int primindx = 0; primindx < pows.size(); primindx++) {
|
for (int primindx = 0; primindx < pows.size(); primindx++) {
|
||||||
int ex = pows.elementAt(primindx).intValue();
|
final int ex = pows.elementAt(primindx).intValue();
|
||||||
final BigInteger p = primes.at(primindx);
|
final BigInteger p = primes.at(primindx);
|
||||||
n = n.multiply(p.pow(ex));
|
n = n.multiply(p.pow(ex));
|
||||||
primeexp.add(new Integer(p.intValue()));
|
primeexp.add(new Integer(p.intValue()));
|
||||||
primeexp.add(new Integer(ex));
|
primeexp.add(new Integer(ex));
|
||||||
}
|
}
|
||||||
} else
|
} else {
|
||||||
n = BigInteger.ZERO;
|
n = BigInteger.ZERO;
|
||||||
|
}
|
||||||
} /* Ifactor */
|
} /* Ifactor */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -167,7 +170,7 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* Vector<Integer> p = (Vector<Integer>)primeexp.clone();
|
* Vector<Integer> p = (Vector<Integer>)primeexp.clone();
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
Ifactor cl = new Ifactor(0);
|
final Ifactor cl = new Ifactor(0);
|
||||||
cl.n = new BigInteger("" + n);
|
cl.n = new BigInteger("" + n);
|
||||||
return cl;
|
return cl;
|
||||||
} /* Ifactor.clone */
|
} /* Ifactor.clone */
|
||||||
@ -267,7 +270,7 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* @return the product, gcd or lcm of both numbers.
|
* @return the product, gcd or lcm of both numbers.
|
||||||
*/
|
*/
|
||||||
protected Ifactor multGcdLcm(final Ifactor oth, int type) {
|
protected Ifactor multGcdLcm(final Ifactor oth, int type) {
|
||||||
Ifactor prod = new Ifactor(0);
|
final Ifactor prod = new Ifactor(0);
|
||||||
/*
|
/*
|
||||||
* skip the case where 0*something =0, falling thru to the empty
|
* skip the case where 0*something =0, falling thru to the empty
|
||||||
* representation for 0
|
* representation for 0
|
||||||
@ -278,19 +281,19 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* Cases of lcm(1, something) return something.
|
* Cases of lcm(1, something) return something.
|
||||||
* Cases of gcd(1, something) return 1.
|
* Cases of gcd(1, something) return 1.
|
||||||
*/
|
*/
|
||||||
if (primeexp.firstElement().intValue() == 1 && type == 0)
|
if (primeexp.firstElement().intValue() == 1 && type == 0) {
|
||||||
return oth;
|
return oth;
|
||||||
else if (primeexp.firstElement().intValue() == 1 && type == 2)
|
} else if (primeexp.firstElement().intValue() == 1 && type == 2) {
|
||||||
return oth;
|
return oth;
|
||||||
else if (primeexp.firstElement().intValue() == 1 && type == 1)
|
} else if (primeexp.firstElement().intValue() == 1 && type == 1) {
|
||||||
return this;
|
return this;
|
||||||
else if (oth.primeexp.firstElement().intValue() == 1 && type == 0)
|
} else if (oth.primeexp.firstElement().intValue() == 1 && type == 0) {
|
||||||
return this;
|
return this;
|
||||||
else if (oth.primeexp.firstElement().intValue() == 1 && type == 2)
|
} else if (oth.primeexp.firstElement().intValue() == 1 && type == 2) {
|
||||||
return this;
|
return this;
|
||||||
else if (oth.primeexp.firstElement().intValue() == 1 && type == 1)
|
} else if (oth.primeexp.firstElement().intValue() == 1 && type == 1) {
|
||||||
return oth;
|
return oth;
|
||||||
else {
|
} else {
|
||||||
int idxThis = 0;
|
int idxThis = 0;
|
||||||
int idxOth = 0;
|
int idxOth = 0;
|
||||||
switch (type) {
|
switch (type) {
|
||||||
@ -417,10 +420,11 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
/*
|
/*
|
||||||
* avoid refactorization if oth is zero...
|
* avoid refactorization if oth is zero...
|
||||||
*/
|
*/
|
||||||
if (oth.compareTo(BigInteger.ZERO) != 0)
|
if (oth.compareTo(BigInteger.ZERO) != 0) {
|
||||||
return new Ifactor(n.add(oth));
|
return new Ifactor(n.add(oth));
|
||||||
else
|
} else {
|
||||||
return this;
|
return this;
|
||||||
|
}
|
||||||
} /* Ifactor.add */
|
} /* Ifactor.add */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -434,22 +438,23 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
/*
|
/*
|
||||||
* three simple cases first
|
* three simple cases first
|
||||||
*/
|
*/
|
||||||
if (exponent < 0)
|
if (exponent < 0) {
|
||||||
throw new ArithmeticException("Cannot raise " + toString() + " to negative " + exponent);
|
throw new ArithmeticException("Cannot raise " + toString() + " to negative " + exponent);
|
||||||
else if (exponent == 0)
|
} else if (exponent == 0) {
|
||||||
return new Ifactor(1);
|
return new Ifactor(1);
|
||||||
else if (exponent == 1)
|
} else if (exponent == 1) {
|
||||||
return this;
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* general case, the vector with the prime factor powers, which are
|
* general case, the vector with the prime factor powers, which are
|
||||||
* component-wise
|
* component-wise
|
||||||
* exponentiation of the individual prime factor powers.
|
* exponentiation of the individual prime factor powers.
|
||||||
*/
|
*/
|
||||||
Ifactor pows = new Ifactor(0);
|
final Ifactor pows = new Ifactor(0);
|
||||||
for (int i = 0; i < primeexp.size(); i += 2) {
|
for (int i = 0; i < primeexp.size(); i += 2) {
|
||||||
Integer p = primeexp.elementAt(i);
|
final Integer p = primeexp.elementAt(i);
|
||||||
int ex = primeexp.elementAt(i + 1).intValue();
|
final int ex = primeexp.elementAt(i + 1).intValue();
|
||||||
pows.primeexp.add(p);
|
pows.primeexp.add(p);
|
||||||
pows.primeexp.add(new Integer(ex * exponent));
|
pows.primeexp.add(new Integer(ex * exponent));
|
||||||
}
|
}
|
||||||
@ -469,24 +474,25 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* @since 2009-05-18
|
* @since 2009-05-18
|
||||||
*/
|
*/
|
||||||
public Rational root(final int r) throws ArithmeticException, Error {
|
public Rational root(final int r) throws ArithmeticException, Error {
|
||||||
if (r == 0)
|
if (r == 0) {
|
||||||
throw new ArithmeticException("Cannot pull zeroth root of " + toString());
|
throw new ArithmeticException("Cannot pull zeroth root of " + toString());
|
||||||
else if (r < 0) {
|
} else if (r < 0) {
|
||||||
/*
|
/*
|
||||||
* a^(-1/b)= 1/(a^(1/b))
|
* a^(-1/b)= 1/(a^(1/b))
|
||||||
*/
|
*/
|
||||||
final Rational invRoot = root(-r);
|
final Rational invRoot = root(-r);
|
||||||
return Rational.ONE.divide(invRoot);
|
return Rational.ONE.divide(invRoot);
|
||||||
} else {
|
} else {
|
||||||
BigInteger pows = BigInteger.ONE;
|
final BigInteger pows = BigInteger.ONE;
|
||||||
for (int i = 0; i < primeexp.size(); i += 2) {
|
for (int i = 0; i < primeexp.size(); i += 2) {
|
||||||
/*
|
/*
|
||||||
* all exponents must be multiples of r to succeed (that is, to
|
* all exponents must be multiples of r to succeed (that is, to
|
||||||
* stay in the range of rational results).
|
* stay in the range of rational results).
|
||||||
*/
|
*/
|
||||||
int ex = primeexp.elementAt(i + 1).intValue();
|
final int ex = primeexp.elementAt(i + 1).intValue();
|
||||||
if (ex % r != 0)
|
if (ex % r != 0) {
|
||||||
throw new ArithmeticException("Cannot pull " + r + "th root of " + toString());
|
throw new ArithmeticException("Cannot pull " + r + "th root of " + toString());
|
||||||
|
}
|
||||||
|
|
||||||
pows.multiply(new BigInteger("" + primeexp.elementAt(i)).pow(ex / r));
|
pows.multiply(new BigInteger("" + primeexp.elementAt(i)).pow(ex / r));
|
||||||
}
|
}
|
||||||
@ -512,18 +518,19 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* multiplied
|
* multiplied
|
||||||
* by 1 or by a product that contains the factors p1..py.
|
* by 1 or by a product that contains the factors p1..py.
|
||||||
*/
|
*/
|
||||||
Vector<BigInteger> d = new Vector<>();
|
final Vector<BigInteger> d = new Vector<>();
|
||||||
if (n.compareTo(BigInteger.ZERO) == 0)
|
if (n.compareTo(BigInteger.ZERO) == 0) {
|
||||||
return d;
|
return d;
|
||||||
|
}
|
||||||
d.add(BigInteger.ONE);
|
d.add(BigInteger.ONE);
|
||||||
if (n.compareTo(BigInteger.ONE) > 0) {
|
if (n.compareTo(BigInteger.ONE) > 0) {
|
||||||
/* Computes sigmaIncopml(p1^e*p2^e2...*py^ey) */
|
/* Computes sigmaIncopml(p1^e*p2^e2...*py^ey) */
|
||||||
Ifactor dp = dropPrime();
|
final Ifactor dp = dropPrime();
|
||||||
|
|
||||||
/* get ez */
|
/* get ez */
|
||||||
final int ez = primeexp.lastElement().intValue();
|
final int ez = primeexp.lastElement().intValue();
|
||||||
|
|
||||||
Vector<BigInteger> partd = dp.divisors();
|
final Vector<BigInteger> partd = dp.divisors();
|
||||||
|
|
||||||
/* obtain pz by lookup in the prime list */
|
/* obtain pz by lookup in the prime list */
|
||||||
final BigInteger pz = new BigInteger(primeexp.elementAt(primeexp.size() - 2).toString());
|
final BigInteger pz = new BigInteger(primeexp.elementAt(primeexp.size() - 2).toString());
|
||||||
@ -532,12 +539,14 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* the output contains all products of the form partd[]*pz^ez, ez>0,
|
* the output contains all products of the form partd[]*pz^ez, ez>0,
|
||||||
* and with the exception of the 1, all these are appended.
|
* and with the exception of the 1, all these are appended.
|
||||||
*/
|
*/
|
||||||
for (int i = 1; i < partd.size(); i++)
|
for (int i = 1; i < partd.size(); i++) {
|
||||||
d.add(partd.elementAt(i));
|
d.add(partd.elementAt(i));
|
||||||
|
}
|
||||||
for (int e = 1; e <= ez; e++) {
|
for (int e = 1; e <= ez; e++) {
|
||||||
final BigInteger pzez = pz.pow(e);
|
final BigInteger pzez = pz.pow(e);
|
||||||
for (int i = 0; i < partd.size(); i++)
|
for (int i = 0; i < partd.size(); i++) {
|
||||||
d.add(partd.elementAt(i).multiply(pzez));
|
d.add(partd.elementAt(i).multiply(pzez));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Collections.sort(d);
|
Collections.sort(d);
|
||||||
@ -563,29 +572,29 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* the question is whether keeping a factorization is worth the effort
|
* the question is whether keeping a factorization is worth the effort
|
||||||
* or whether one should simply multiply these to return a BigInteger...
|
* or whether one should simply multiply these to return a BigInteger...
|
||||||
*/
|
*/
|
||||||
if (n.compareTo(BigInteger.ONE) == 0)
|
if (n.compareTo(BigInteger.ONE) == 0) {
|
||||||
return ONE;
|
return ONE;
|
||||||
else if (n.compareTo(BigInteger.ZERO) == 0)
|
} else if (n.compareTo(BigInteger.ZERO) == 0) {
|
||||||
return ZERO;
|
return ZERO;
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* multiplicative: sigma_k(p^e) = [p^(k*(e+1))-1]/[p^k-1]
|
* multiplicative: sigma_k(p^e) = [p^(k*(e+1))-1]/[p^k-1]
|
||||||
* sigma_0(p^e) = e+1.
|
* sigma_0(p^e) = e+1.
|
||||||
*/
|
*/
|
||||||
Ifactor resul = Ifactor.ONE;
|
Ifactor resul = Ifactor.ONE;
|
||||||
for (int i = 0; i < primeexp.size(); i += 2) {
|
for (int i = 0; i < primeexp.size(); i += 2) {
|
||||||
int ex = primeexp.elementAt(i + 1).intValue();
|
final int ex = primeexp.elementAt(i + 1).intValue();
|
||||||
if (k == 0)
|
if (k == 0) {
|
||||||
resul = resul.multiply(ex + 1);
|
resul = resul.multiply(ex + 1);
|
||||||
else {
|
} else {
|
||||||
Integer p = primeexp.elementAt(i);
|
final Integer p = primeexp.elementAt(i);
|
||||||
BigInteger num = (new BigInteger(p.toString())).pow(k * (ex + 1)).subtract(BigInteger.ONE);
|
final BigInteger num = (new BigInteger(p.toString())).pow(k * (ex + 1)).subtract(BigInteger.ONE);
|
||||||
BigInteger deno = (new BigInteger(p.toString())).pow(k).subtract(BigInteger.ONE);
|
final BigInteger deno = (new BigInteger(p.toString())).pow(k).subtract(BigInteger.ONE);
|
||||||
/*
|
/*
|
||||||
* This division is of course exact, no remainder
|
* This division is of course exact, no remainder
|
||||||
* The costly prime factorization is hidden here.
|
* The costly prime factorization is hidden here.
|
||||||
*/
|
*/
|
||||||
Ifactor f = new Ifactor(num.divide(deno));
|
final Ifactor f = new Ifactor(num.divide(deno));
|
||||||
resul = resul.multiply(f);
|
resul = resul.multiply(f);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -608,8 +617,9 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
/*
|
/*
|
||||||
* the cases n==1 or n ==0
|
* the cases n==1 or n ==0
|
||||||
*/
|
*/
|
||||||
if (n.compareTo(BigInteger.ONE) <= 0)
|
if (n.compareTo(BigInteger.ONE) <= 0) {
|
||||||
return this;
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The cases n>1
|
* The cases n>1
|
||||||
@ -617,13 +627,13 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* the vector with the new prime factor powers, which contain the
|
* the vector with the new prime factor powers, which contain the
|
||||||
* old prime factor powers up to but not including the last one.
|
* old prime factor powers up to but not including the last one.
|
||||||
*/
|
*/
|
||||||
Ifactor pows = new Ifactor(0);
|
final Ifactor pows = new Ifactor(0);
|
||||||
pows.n = BigInteger.ONE;
|
pows.n = BigInteger.ONE;
|
||||||
for (int i = 0; i < primeexp.size() - 2; i += 2) {
|
for (int i = 0; i < primeexp.size() - 2; i += 2) {
|
||||||
pows.primeexp.add(primeexp.elementAt(i));
|
pows.primeexp.add(primeexp.elementAt(i));
|
||||||
pows.primeexp.add(primeexp.elementAt(i + 1));
|
pows.primeexp.add(primeexp.elementAt(i + 1));
|
||||||
BigInteger p = new BigInteger(primeexp.elementAt(i).toString());
|
final BigInteger p = new BigInteger(primeexp.elementAt(i).toString());
|
||||||
int ex = primeexp.elementAt(i + 1).intValue();
|
final int ex = primeexp.elementAt(i + 1).intValue();
|
||||||
pows.n = pows.n.multiply(p.pow(ex));
|
pows.n = pows.n.multiply(p.pow(ex));
|
||||||
}
|
}
|
||||||
return pows;
|
return pows;
|
||||||
@ -639,8 +649,9 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* check the exponents, located at the odd-indexed positions
|
* check the exponents, located at the odd-indexed positions
|
||||||
*/
|
*/
|
||||||
for (int i = 1; i < primeexp.size(); i += 2) {
|
for (int i = 1; i < primeexp.size(); i += 2) {
|
||||||
if (primeexp.elementAt(i).intValue() % 2 != 0)
|
if (primeexp.elementAt(i).intValue() % 2 != 0) {
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
} /* Ifactor.issquare */
|
} /* Ifactor.issquare */
|
||||||
@ -652,8 +663,9 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
*/
|
*/
|
||||||
public int bigomega() {
|
public int bigomega() {
|
||||||
int resul = 0;
|
int resul = 0;
|
||||||
for (int i = 1; i < primeexp.size(); i += 2)
|
for (int i = 1; i < primeexp.size(); i += 2) {
|
||||||
resul += primeexp.elementAt(i).intValue();
|
resul += primeexp.elementAt(i).intValue();
|
||||||
|
}
|
||||||
return (resul);
|
return (resul);
|
||||||
} /* Ifactor.bigomega */
|
} /* Ifactor.bigomega */
|
||||||
|
|
||||||
@ -675,9 +687,11 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
*/
|
*/
|
||||||
public BigInteger core() {
|
public BigInteger core() {
|
||||||
BigInteger resul = BigInteger.ONE;
|
BigInteger resul = BigInteger.ONE;
|
||||||
for (int i = 0; i < primeexp.size(); i += 2)
|
for (int i = 0; i < primeexp.size(); i += 2) {
|
||||||
if (primeexp.elementAt(i + 1).intValue() % 2 != 0)
|
if (primeexp.elementAt(i + 1).intValue() % 2 != 0) {
|
||||||
resul = resul.multiply(new BigInteger(primeexp.elementAt(i).toString()));
|
resul = resul.multiply(new BigInteger(primeexp.elementAt(i).toString()));
|
||||||
|
}
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* Ifactor.core */
|
} /* Ifactor.core */
|
||||||
|
|
||||||
@ -690,17 +704,19 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* @return the moebius function.
|
* @return the moebius function.
|
||||||
*/
|
*/
|
||||||
public int moebius() {
|
public int moebius() {
|
||||||
if (n.compareTo(BigInteger.ONE) <= 0)
|
if (n.compareTo(BigInteger.ONE) <= 0) {
|
||||||
return 1;
|
return 1;
|
||||||
|
}
|
||||||
/* accumulate number of different primes in k */
|
/* accumulate number of different primes in k */
|
||||||
int k = 1;
|
int k = 1;
|
||||||
for (int i = 0; i < primeexp.size(); i += 2) {
|
for (int i = 0; i < primeexp.size(); i += 2) {
|
||||||
final int e = primeexp.elementAt(i + 1).intValue();
|
final int e = primeexp.elementAt(i + 1).intValue();
|
||||||
if (e > 1)
|
if (e > 1) {
|
||||||
return 0;
|
return 0;
|
||||||
else if (e == 1)
|
} else if (e == 1) {
|
||||||
/* accumulates (-1)^k */
|
/* accumulates (-1)^k */
|
||||||
k *= -1;
|
k *= -1;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
return (k);
|
return (k);
|
||||||
@ -714,10 +730,11 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* @return the larger of the two values.
|
* @return the larger of the two values.
|
||||||
*/
|
*/
|
||||||
public Ifactor max(final Ifactor oth) {
|
public Ifactor max(final Ifactor oth) {
|
||||||
if (n.compareTo(oth.n) >= 0)
|
if (n.compareTo(oth.n) >= 0) {
|
||||||
return this;
|
return this;
|
||||||
else
|
} else {
|
||||||
return oth;
|
return oth;
|
||||||
|
}
|
||||||
} /* Ifactor.max */
|
} /* Ifactor.max */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -728,10 +745,11 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* @return the smaller of the two values.
|
* @return the smaller of the two values.
|
||||||
*/
|
*/
|
||||||
public Ifactor min(final Ifactor oth) {
|
public Ifactor min(final Ifactor oth) {
|
||||||
if (n.compareTo(oth.n) <= 0)
|
if (n.compareTo(oth.n) <= 0) {
|
||||||
return this;
|
return this;
|
||||||
else
|
} else {
|
||||||
return oth;
|
return oth;
|
||||||
|
}
|
||||||
} /* Ifactor.min */
|
} /* Ifactor.min */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -743,8 +761,9 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
*/
|
*/
|
||||||
public static Ifactor max(final Vector<Ifactor> set) {
|
public static Ifactor max(final Vector<Ifactor> set) {
|
||||||
Ifactor resul = set.elementAt(0);
|
Ifactor resul = set.elementAt(0);
|
||||||
for (int i = 1; i < set.size(); i++)
|
for (int i = 1; i < set.size(); i++) {
|
||||||
resul = resul.max(set.elementAt(i));
|
resul = resul.max(set.elementAt(i));
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* Ifactor.max */
|
} /* Ifactor.max */
|
||||||
|
|
||||||
@ -757,8 +776,9 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
*/
|
*/
|
||||||
public static Ifactor min(final Vector<Ifactor> set) {
|
public static Ifactor min(final Vector<Ifactor> set) {
|
||||||
Ifactor resul = set.elementAt(0);
|
Ifactor resul = set.elementAt(0);
|
||||||
for (int i = 1; i < set.size(); i++)
|
for (int i = 1; i < set.size(); i++) {
|
||||||
resul = resul.min(set.elementAt(i));
|
resul = resul.min(set.elementAt(i));
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* Ifactor.min */
|
} /* Ifactor.min */
|
||||||
|
|
||||||
@ -784,17 +804,19 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
String resul = new String(n.toString() + ":");
|
String resul = new String(n.toString() + ":");
|
||||||
if (n.compareTo(BigInteger.ONE) == 0)
|
if (n.compareTo(BigInteger.ONE) == 0) {
|
||||||
resul += "1";
|
resul += "1";
|
||||||
else {
|
} else {
|
||||||
boolean firstMul = true;
|
boolean firstMul = true;
|
||||||
for (int i = 0; i < primeexp.size(); i += 2) {
|
for (int i = 0; i < primeexp.size(); i += 2) {
|
||||||
if (!firstMul)
|
if (!firstMul) {
|
||||||
resul += "*";
|
resul += "*";
|
||||||
if (primeexp.elementAt(i + 1).intValue() > 1)
|
}
|
||||||
|
if (primeexp.elementAt(i + 1).intValue() > 1) {
|
||||||
resul += primeexp.elementAt(i).toString() + "^" + primeexp.elementAt(i + 1).toString();
|
resul += primeexp.elementAt(i).toString() + "^" + primeexp.elementAt(i + 1).toString();
|
||||||
else
|
} else {
|
||||||
resul += primeexp.elementAt(i).toString();
|
resul += primeexp.elementAt(i).toString();
|
||||||
|
}
|
||||||
firstMul = false;
|
firstMul = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -807,7 +829,7 @@ public class Ifactor implements Cloneable, Comparable<Ifactor> {
|
|||||||
* java -cp . org.nevec.rjm.Ifactor n<br>
|
* java -cp . org.nevec.rjm.Ifactor n<br>
|
||||||
*/
|
*/
|
||||||
public static void main(String[] args) throws Exception {
|
public static void main(String[] args) throws Exception {
|
||||||
BigInteger n = new BigInteger(args[0]);
|
final BigInteger n = new BigInteger(args[0]);
|
||||||
System.out.println(new Ifactor(n));
|
System.out.println(new Ifactor(n));
|
||||||
} /* Ifactor.main */
|
} /* Ifactor.main */
|
||||||
} /* Ifactor */
|
} /* Ifactor */
|
||||||
|
@ -63,9 +63,9 @@ public class PartitionsP {
|
|||||||
private void growto(BigInteger n) {
|
private void growto(BigInteger n) {
|
||||||
while (a.size() <= n.intValue()) {
|
while (a.size() <= n.intValue()) {
|
||||||
BigInteger per = new BigInteger("0");
|
BigInteger per = new BigInteger("0");
|
||||||
BigInteger cursiz = new BigInteger("" + a.size());
|
final BigInteger cursiz = new BigInteger("" + a.size());
|
||||||
for (int k = 0; k < a.size(); k++) {
|
for (int k = 0; k < a.size(); k++) {
|
||||||
BigInteger tmp = a.elementAt(k).multiply(BigIntegerMath.sigma(a.size() - k));
|
final BigInteger tmp = a.elementAt(k).multiply(BigIntegerMath.sigma(a.size() - k));
|
||||||
per = per.add(tmp);
|
per = per.add(tmp);
|
||||||
}
|
}
|
||||||
a.add(per.divide(cursiz));
|
a.add(per.divide(cursiz));
|
||||||
@ -81,8 +81,8 @@ public class PartitionsP {
|
|||||||
* @since 2008-10-15
|
* @since 2008-10-15
|
||||||
*/
|
*/
|
||||||
public static void main(String[] args) throws Exception {
|
public static void main(String[] args) throws Exception {
|
||||||
PartitionsP a = new PartitionsP();
|
final PartitionsP a = new PartitionsP();
|
||||||
int n = (new Integer(args[0])).intValue();
|
final int n = (new Integer(args[0])).intValue();
|
||||||
System.out.println("P(" + n + ")=" + a.at(n));
|
System.out.println("P(" + n + ")=" + a.at(n));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -86,38 +86,34 @@ public class Prime {
|
|||||||
/*
|
/*
|
||||||
* numbers less than 2 are not prime
|
* numbers less than 2 are not prime
|
||||||
*/
|
*/
|
||||||
if (n.compareTo(two) == -1)
|
if (n.compareTo(two) == -1) {
|
||||||
return false;
|
return false;
|
||||||
/*
|
} else if (n.compareTo(two) == 0) {
|
||||||
* 2 is prime
|
|
||||||
*/
|
|
||||||
else if (n.compareTo(two) == 0)
|
|
||||||
return true;
|
return true;
|
||||||
/*
|
} else if (n.remainder(two).compareTo(BigInteger.ZERO) == 0) {
|
||||||
* even numbers >2 are not prime
|
|
||||||
*/
|
|
||||||
else if (n.remainder(two).compareTo(BigInteger.ZERO) == 0)
|
|
||||||
return false;
|
return false;
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* q= n- 1 = d *2^s with d odd
|
* q= n- 1 = d *2^s with d odd
|
||||||
*/
|
*/
|
||||||
final BigInteger q = n.subtract(BigInteger.ONE);
|
final BigInteger q = n.subtract(BigInteger.ONE);
|
||||||
int s = q.getLowestSetBit();
|
final int s = q.getLowestSetBit();
|
||||||
BigInteger d = q.shiftRight(s);
|
final BigInteger d = q.shiftRight(s);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* test whether a^d = 1 (mod n)
|
* test whether a^d = 1 (mod n)
|
||||||
*/
|
*/
|
||||||
if (a.modPow(d, n).compareTo(BigInteger.ONE) == 0)
|
if (a.modPow(d, n).compareTo(BigInteger.ONE) == 0) {
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* test whether a^(d*2^r) = -1 (mod n), 0<=r<s
|
* test whether a^(d*2^r) = -1 (mod n), 0<=r<s
|
||||||
*/
|
*/
|
||||||
for (int r = 0; r < s; r++) {
|
for (int r = 0; r < s; r++) {
|
||||||
if (a.modPow(d.shiftLeft(r), n).compareTo(q) == 0)
|
if (a.modPow(d.shiftLeft(r), n).compareTo(q) == 0) {
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -140,28 +136,29 @@ public class Prime {
|
|||||||
final String[] mr = { "2047", "1373653", "25326001", "3215031751", "2152302898747", "3474749660383", "341550071728321" };
|
final String[] mr = { "2047", "1373653", "25326001", "3215031751", "2152302898747", "3474749660383", "341550071728321" };
|
||||||
int mrLim = 0;
|
int mrLim = 0;
|
||||||
while (mrLim < mr.length) {
|
while (mrLim < mr.length) {
|
||||||
int l = n.compareTo(new BigInteger(mr[mrLim]));
|
final int l = n.compareTo(new BigInteger(mr[mrLim]));
|
||||||
if (l < 0)
|
if (l < 0) {
|
||||||
break;
|
break;
|
||||||
/*
|
} else if (l == 0) {
|
||||||
* if one of the pseudo-primes: this is a composite
|
|
||||||
*/
|
|
||||||
else if (l == 0)
|
|
||||||
return -1;
|
return -1;
|
||||||
|
}
|
||||||
mrLim++;
|
mrLim++;
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* cannot test candidates larger than the last in the mr list
|
* cannot test candidates larger than the last in the mr list
|
||||||
*/
|
*/
|
||||||
if (mrLim == mr.length)
|
if (mrLim == mr.length) {
|
||||||
return 0;
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* test the bases prime(1), prime(2) up to prime(mrLim+1)
|
* test the bases prime(1), prime(2) up to prime(mrLim+1)
|
||||||
*/
|
*/
|
||||||
for (int p = 0; p <= mrLim; p++)
|
for (int p = 0; p <= mrLim; p++) {
|
||||||
if (isSPP(n, at(p)) == false)
|
if (isSPP(n, at(p)) == false) {
|
||||||
return -1;
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -197,9 +194,11 @@ public class Prime {
|
|||||||
*/
|
*/
|
||||||
growto(n);
|
growto(n);
|
||||||
BigInteger r = new BigInteger("0");
|
BigInteger r = new BigInteger("0");
|
||||||
for (int i = 0; i < a.size(); i++)
|
for (int i = 0; i < a.size(); i++) {
|
||||||
if (a.elementAt(i).compareTo(n) <= 0)
|
if (a.elementAt(i).compareTo(n) <= 0) {
|
||||||
r = r.add(BigInteger.ONE);
|
r = r.add(BigInteger.ONE);
|
||||||
|
}
|
||||||
|
}
|
||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -213,8 +212,9 @@ public class Prime {
|
|||||||
*/
|
*/
|
||||||
public BigInteger nextprime(BigInteger n) {
|
public BigInteger nextprime(BigInteger n) {
|
||||||
/* if n <=1, return 2 */
|
/* if n <=1, return 2 */
|
||||||
if (n.compareTo(BigInteger.ONE) <= 0)
|
if (n.compareTo(BigInteger.ONE) <= 0) {
|
||||||
return (a.elementAt(0));
|
return (a.elementAt(0));
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If the currently largest element in the list is too small, increase
|
* If the currently largest element in the list is too small, increase
|
||||||
@ -224,9 +224,11 @@ public class Prime {
|
|||||||
while (a.lastElement().compareTo(n) <= 0) {
|
while (a.lastElement().compareTo(n) <= 0) {
|
||||||
growto(nMax.add(new BigInteger("" + 5)));
|
growto(nMax.add(new BigInteger("" + 5)));
|
||||||
}
|
}
|
||||||
for (int i = 0; i < a.size(); i++)
|
for (int i = 0; i < a.size(); i++) {
|
||||||
if (a.elementAt(i).compareTo(n) == 1)
|
if (a.elementAt(i).compareTo(n) == 1) {
|
||||||
return (a.elementAt(i));
|
return (a.elementAt(i));
|
||||||
|
}
|
||||||
|
}
|
||||||
return (a.lastElement());
|
return (a.lastElement());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -240,20 +242,24 @@ public class Prime {
|
|||||||
*/
|
*/
|
||||||
public BigInteger prevprime(BigInteger n) {
|
public BigInteger prevprime(BigInteger n) {
|
||||||
/* if n <=2, return 0 */
|
/* if n <=2, return 0 */
|
||||||
if (n.compareTo(BigInteger.ONE) <= 0)
|
if (n.compareTo(BigInteger.ONE) <= 0) {
|
||||||
return BigInteger.ZERO;
|
return BigInteger.ZERO;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* If the currently largest element in the list is too small, increase
|
* If the currently largest element in the list is too small, increase
|
||||||
* in intervals
|
* in intervals
|
||||||
* of 5 until the list has at least i elements.
|
* of 5 until the list has at least i elements.
|
||||||
*/
|
*/
|
||||||
while (a.lastElement().compareTo(n) < 0)
|
while (a.lastElement().compareTo(n) < 0) {
|
||||||
growto(nMax.add(new BigInteger("" + 5)));
|
growto(nMax.add(new BigInteger("" + 5)));
|
||||||
|
}
|
||||||
|
|
||||||
for (int i = 0; i < a.size(); i++)
|
for (int i = 0; i < a.size(); i++) {
|
||||||
if (a.elementAt(i).compareTo(n) >= 0)
|
if (a.elementAt(i).compareTo(n) >= 0) {
|
||||||
return (a.elementAt(i - 1));
|
return (a.elementAt(i - 1));
|
||||||
|
}
|
||||||
|
}
|
||||||
return (a.lastElement());
|
return (a.lastElement());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -272,8 +278,9 @@ public class Prime {
|
|||||||
/*
|
/*
|
||||||
* Test the list of known primes only up to sqrt(n)
|
* Test the list of known primes only up to sqrt(n)
|
||||||
*/
|
*/
|
||||||
if (a.get(p).multiply(a.get(p)).compareTo(nMax) == 1)
|
if (a.get(p).multiply(a.get(p)).compareTo(nMax) == 1) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The next case means that the p'th number in the list of known
|
* The next case means that the p'th number in the list of known
|
||||||
@ -285,8 +292,9 @@ public class Prime {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (isp)
|
if (isp) {
|
||||||
a.add(nMax);
|
a.add(nMax);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -299,11 +307,12 @@ public class Prime {
|
|||||||
* @since 2006-08-14
|
* @since 2006-08-14
|
||||||
*/
|
*/
|
||||||
public static void main(String[] args) throws Exception {
|
public static void main(String[] args) throws Exception {
|
||||||
Prime a = new Prime();
|
final Prime a = new Prime();
|
||||||
int n = (new Integer(args[0])).intValue();
|
final int n = (new Integer(args[0])).intValue();
|
||||||
if (n >= 1) {
|
if (n >= 1) {
|
||||||
if (n >= 2)
|
if (n >= 2) {
|
||||||
System.out.println("prime(" + (n - 1) + ") = " + a.at(n - 1));
|
System.out.println("prime(" + (n - 1) + ") = " + a.at(n - 1));
|
||||||
|
}
|
||||||
System.out.println("prime(" + n + ") = " + a.at(n));
|
System.out.println("prime(" + n + ") = " + a.at(n));
|
||||||
System.out.println("prime(" + (n + 1) + ") = " + a.at(n + 1));
|
System.out.println("prime(" + (n + 1) + ") = " + a.at(n + 1));
|
||||||
System.out.println("pi(" + n + ") = " + a.pi(new BigInteger("" + n)));
|
System.out.println("pi(" + n + ") = " + a.pi(new BigInteger("" + n)));
|
||||||
|
@ -43,8 +43,9 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
public RatPoly(final Vector<Rational> L) {
|
public RatPoly(final Vector<Rational> L) {
|
||||||
a = new Vector<>();
|
a = new Vector<>();
|
||||||
for (int i = 0; i < L.size(); i++)
|
for (int i = 0; i < L.size(); i++) {
|
||||||
a.add(L.elementAt(i).clone());
|
a.add(L.elementAt(i).clone());
|
||||||
|
}
|
||||||
simplify();
|
simplify();
|
||||||
} /* ctor */
|
} /* ctor */
|
||||||
|
|
||||||
@ -56,10 +57,10 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
public RatPoly(final String L) throws NumberFormatException {
|
public RatPoly(final String L) throws NumberFormatException {
|
||||||
a = new Vector<>();
|
a = new Vector<>();
|
||||||
Scanner sc = new Scanner(L);
|
final Scanner sc = new Scanner(L);
|
||||||
sc.useDelimiter(",");
|
sc.useDelimiter(",");
|
||||||
while (sc.hasNext()) {
|
while (sc.hasNext()) {
|
||||||
String tok = sc.next();
|
final String tok = sc.next();
|
||||||
a.add(new Rational(tok));
|
a.add(new Rational(tok));
|
||||||
}
|
}
|
||||||
simplify();
|
simplify();
|
||||||
@ -103,16 +104,18 @@ class RatPoly {
|
|||||||
BigInteger Nmax = BigInteger.ONE.negate();
|
BigInteger Nmax = BigInteger.ONE.negate();
|
||||||
for (int j = 0; j < A.size(); j++) {
|
for (int j = 0; j < A.size(); j++) {
|
||||||
if (A.elementAt(j).compareTo(BigInteger.ZERO) <= 0) {
|
if (A.elementAt(j).compareTo(BigInteger.ZERO) <= 0) {
|
||||||
if (Nmax.compareTo(BigInteger.ZERO) < 0)
|
if (Nmax.compareTo(BigInteger.ZERO) < 0) {
|
||||||
Nmax = A.elementAt(j).negate();
|
Nmax = A.elementAt(j).negate();
|
||||||
else
|
} else {
|
||||||
Nmax = Nmax.min(A.elementAt(j).negate());
|
Nmax = Nmax.min(A.elementAt(j).negate());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (Nmax.compareTo(BigInteger.ZERO) < 0)
|
if (Nmax.compareTo(BigInteger.ZERO) < 0) {
|
||||||
throw new ArithmeticException("Infinite Number of Terms in Series " + Nmax.toString());
|
throw new ArithmeticException("Infinite Number of Terms in Series " + Nmax.toString());
|
||||||
|
}
|
||||||
|
|
||||||
int nmax = Nmax.intValue() - 1;
|
final int nmax = Nmax.intValue() - 1;
|
||||||
init(A, B, nmax);
|
init(A, B, nmax);
|
||||||
} /* ctor */
|
} /* ctor */
|
||||||
|
|
||||||
@ -130,15 +133,15 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
protected void init(final Vector<BigInteger> A, final Vector<BigInteger> B, int nmax) throws Error {
|
protected void init(final Vector<BigInteger> A, final Vector<BigInteger> B, int nmax) throws Error {
|
||||||
a = new Vector<>();
|
a = new Vector<>();
|
||||||
Factorial f = new Factorial();
|
final Factorial f = new Factorial();
|
||||||
for (int n = 0; n <= nmax; n++) {
|
for (int n = 0; n <= nmax; n++) {
|
||||||
Rational c = new Rational(1, 1);
|
Rational c = new Rational(1, 1);
|
||||||
for (int j = 0; j < A.size(); j++) {
|
for (int j = 0; j < A.size(); j++) {
|
||||||
Rational aEl = new Rational(A.elementAt(j));
|
final Rational aEl = new Rational(A.elementAt(j));
|
||||||
c = c.multiply(aEl.Pochhammer(n));
|
c = c.multiply(aEl.Pochhammer(n));
|
||||||
}
|
}
|
||||||
for (int j = 0; j < B.size(); j++) {
|
for (int j = 0; j < B.size(); j++) {
|
||||||
Rational bEl = new Rational(B.elementAt(j));
|
final Rational bEl = new Rational(B.elementAt(j));
|
||||||
c = c.divide(bEl.Pochhammer(n));
|
c = c.divide(bEl.Pochhammer(n));
|
||||||
}
|
}
|
||||||
c = c.divide(f.at(n));
|
c = c.divide(f.at(n));
|
||||||
@ -155,7 +158,7 @@ class RatPoly {
|
|||||||
@Override
|
@Override
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public RatPoly clone() {
|
public RatPoly clone() {
|
||||||
RatPoly clo = new RatPoly();
|
final RatPoly clo = new RatPoly();
|
||||||
clo.a = (Vector<Rational>) a.clone();
|
clo.a = (Vector<Rational>) a.clone();
|
||||||
return clo;
|
return clo;
|
||||||
} /* clone */
|
} /* clone */
|
||||||
@ -169,10 +172,11 @@ class RatPoly {
|
|||||||
* @return the polynomial coefficient in front of x^n.
|
* @return the polynomial coefficient in front of x^n.
|
||||||
*/
|
*/
|
||||||
public Rational at(final int n) {
|
public Rational at(final int n) {
|
||||||
if (n < a.size())
|
if (n < a.size()) {
|
||||||
return (a.elementAt(n));
|
return (a.elementAt(n));
|
||||||
else
|
} else {
|
||||||
return (new Rational(0, 1));
|
return (new Rational(0, 1));
|
||||||
|
}
|
||||||
} /* at */
|
} /* at */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -187,8 +191,9 @@ class RatPoly {
|
|||||||
public BigComplex valueOf(BigComplex x, MathContext mc) {
|
public BigComplex valueOf(BigComplex x, MathContext mc) {
|
||||||
/* result is initialized to zero */
|
/* result is initialized to zero */
|
||||||
BigComplex f = new BigComplex();
|
BigComplex f = new BigComplex();
|
||||||
for (int i = degree(); i >= 0; i--)
|
for (int i = degree(); i >= 0; i--) {
|
||||||
f = f.multiply(x, mc).add(a.elementAt(i).BigDecimalValue(mc));
|
f = f.multiply(x, mc).add(a.elementAt(i).BigDecimalValue(mc));
|
||||||
|
}
|
||||||
return f;
|
return f;
|
||||||
} /* valueOf */
|
} /* valueOf */
|
||||||
|
|
||||||
@ -202,8 +207,9 @@ class RatPoly {
|
|||||||
public Rational valueOf(Rational x) {
|
public Rational valueOf(Rational x) {
|
||||||
/* result is initialized to zero */
|
/* result is initialized to zero */
|
||||||
Rational f = new Rational(0, 1);
|
Rational f = new Rational(0, 1);
|
||||||
for (int i = degree(); i >= 0; i--)
|
for (int i = degree(); i >= 0; i--) {
|
||||||
f = f.multiply(x).add(a.elementAt(i));
|
f = f.multiply(x).add(a.elementAt(i));
|
||||||
|
}
|
||||||
return f;
|
return f;
|
||||||
} /* valueOf */
|
} /* valueOf */
|
||||||
|
|
||||||
@ -240,14 +246,15 @@ class RatPoly {
|
|||||||
* @param value the new value of the coefficient.
|
* @param value the new value of the coefficient.
|
||||||
*/
|
*/
|
||||||
public void set(final int n, final Rational value) {
|
public void set(final int n, final Rational value) {
|
||||||
if (n < a.size())
|
if (n < a.size()) {
|
||||||
a.set(n, value);
|
a.set(n, value);
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* fill intermediate powers with coefficients of zero
|
* fill intermediate powers with coefficients of zero
|
||||||
*/
|
*/
|
||||||
while (a.size() < n)
|
while (a.size() < n) {
|
||||||
a.add(new Rational(0, 1));
|
a.add(new Rational(0, 1));
|
||||||
|
}
|
||||||
a.add(value);
|
a.add(value);
|
||||||
}
|
}
|
||||||
} /* set */
|
} /* set */
|
||||||
@ -265,7 +272,7 @@ class RatPoly {
|
|||||||
* the new value of the coefficient.
|
* the new value of the coefficient.
|
||||||
*/
|
*/
|
||||||
public void set(final int n, final BigInteger value) {
|
public void set(final int n, final BigInteger value) {
|
||||||
Rational val2 = new Rational(value, BigInteger.ONE);
|
final Rational val2 = new Rational(value, BigInteger.ONE);
|
||||||
set(n, val2);
|
set(n, val2);
|
||||||
} /* set */
|
} /* set */
|
||||||
|
|
||||||
@ -282,7 +289,7 @@ class RatPoly {
|
|||||||
* the new value of the coefficient.
|
* the new value of the coefficient.
|
||||||
*/
|
*/
|
||||||
public void set(final int n, final int value) {
|
public void set(final int n, final int value) {
|
||||||
Rational val2 = new Rational(value, 1);
|
final Rational val2 = new Rational(value, 1);
|
||||||
set(n, val2);
|
set(n, val2);
|
||||||
} /* set */
|
} /* set */
|
||||||
|
|
||||||
@ -293,9 +300,10 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
public void setExp(final int nmax) {
|
public void setExp(final int nmax) {
|
||||||
a.clear();
|
a.clear();
|
||||||
Factorial factorial = new Factorial();
|
final Factorial factorial = new Factorial();
|
||||||
for (int n = 0; n <= nmax; n++)
|
for (int n = 0; n <= nmax; n++) {
|
||||||
set(n, new Rational(BigInteger.ONE, factorial.at(n)));
|
set(n, new Rational(BigInteger.ONE, factorial.at(n)));
|
||||||
|
}
|
||||||
} /* setExp */
|
} /* setExp */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -336,9 +344,11 @@ class RatPoly {
|
|||||||
* @since 2010-08-27
|
* @since 2010-08-27
|
||||||
*/
|
*/
|
||||||
public int ldegree() {
|
public int ldegree() {
|
||||||
for (int n = 0; n < a.size(); n++)
|
for (int n = 0; n < a.size(); n++) {
|
||||||
if (a.elementAt(n).compareTo(BigInteger.ZERO) != 0)
|
if (a.elementAt(n).compareTo(BigInteger.ZERO) != 0) {
|
||||||
return n;
|
return n;
|
||||||
|
}
|
||||||
|
}
|
||||||
return 0;
|
return 0;
|
||||||
} /* ldegree */
|
} /* ldegree */
|
||||||
|
|
||||||
@ -352,10 +362,12 @@ class RatPoly {
|
|||||||
* factor.
|
* factor.
|
||||||
*/
|
*/
|
||||||
public RatPoly multiply(final Rational val) {
|
public RatPoly multiply(final Rational val) {
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
if (val.compareTo(BigInteger.ZERO) != 0)
|
if (val.compareTo(BigInteger.ZERO) != 0) {
|
||||||
for (int n = 0; n < a.size(); n++)
|
for (int n = 0; n < a.size(); n++) {
|
||||||
resul.set(n, a.elementAt(n).multiply(val));
|
resul.set(n, a.elementAt(n).multiply(val));
|
||||||
|
}
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* multiply */
|
} /* multiply */
|
||||||
|
|
||||||
@ -370,10 +382,12 @@ class RatPoly {
|
|||||||
* @since 2010-08-27
|
* @since 2010-08-27
|
||||||
*/
|
*/
|
||||||
public RatPoly multiply(final BigInteger val) {
|
public RatPoly multiply(final BigInteger val) {
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
if (val.compareTo(BigInteger.ZERO) != 0)
|
if (val.compareTo(BigInteger.ZERO) != 0) {
|
||||||
for (int n = 0; n < a.size(); n++)
|
for (int n = 0; n < a.size(); n++) {
|
||||||
resul.set(n, a.elementAt(n).multiply(val));
|
resul.set(n, a.elementAt(n).multiply(val));
|
||||||
|
}
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} /* multiply */
|
} /* multiply */
|
||||||
|
|
||||||
@ -385,7 +399,7 @@ class RatPoly {
|
|||||||
* @return the product of this with the other polynomial
|
* @return the product of this with the other polynomial
|
||||||
*/
|
*/
|
||||||
public RatPoly multiply(final RatPoly val) {
|
public RatPoly multiply(final RatPoly val) {
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
/*
|
/*
|
||||||
* the degree of the result is the sum of the two degrees.
|
* the degree of the result is the sum of the two degrees.
|
||||||
*/
|
*/
|
||||||
@ -410,15 +424,16 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
public RatPoly pow(final int n) throws ArithmeticException {
|
public RatPoly pow(final int n) throws ArithmeticException {
|
||||||
RatPoly resul = new RatPoly("1");
|
RatPoly resul = new RatPoly("1");
|
||||||
if (n < 0)
|
if (n < 0) {
|
||||||
throw new ArithmeticException("negative polynomial power " + n);
|
throw new ArithmeticException("negative polynomial power " + n);
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* this ought probably be done with some binary representation
|
* this ought probably be done with some binary representation
|
||||||
* of the power and a smaller number of multiplications.
|
* of the power and a smaller number of multiplications.
|
||||||
*/
|
*/
|
||||||
for (int i = 1; i <= n; i++)
|
for (int i = 1; i <= n; i++) {
|
||||||
resul = resul.multiply(this);
|
resul = resul.multiply(this);
|
||||||
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
return resul;
|
return resul;
|
||||||
}
|
}
|
||||||
@ -447,7 +462,7 @@ class RatPoly {
|
|||||||
* scale the polynomial by division through the expansion coefficient of
|
* scale the polynomial by division through the expansion coefficient of
|
||||||
* the absolute term
|
* the absolute term
|
||||||
*/
|
*/
|
||||||
RatPoly red = divide(a.elementAt(0));
|
final RatPoly red = divide(a.elementAt(0));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* and remove the leading term (now equal to 1)
|
* and remove the leading term (now equal to 1)
|
||||||
@ -477,14 +492,14 @@ class RatPoly {
|
|||||||
* @since 2008-10-25
|
* @since 2008-10-25
|
||||||
*/
|
*/
|
||||||
public RatPoly add(final RatPoly val) {
|
public RatPoly add(final RatPoly val) {
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
/*
|
/*
|
||||||
* the degree of the result is the larger of the two degrees (before
|
* the degree of the result is the larger of the two degrees (before
|
||||||
* simplify() at least).
|
* simplify() at least).
|
||||||
*/
|
*/
|
||||||
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
||||||
for (int n = 0; n <= nmax; n++) {
|
for (int n = 0; n <= nmax; n++) {
|
||||||
Rational coef = at(n).add(val.at(n));
|
final Rational coef = at(n).add(val.at(n));
|
||||||
resul.set(n, coef);
|
resul.set(n, coef);
|
||||||
}
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
@ -500,14 +515,14 @@ class RatPoly {
|
|||||||
* @since 2008-10-25
|
* @since 2008-10-25
|
||||||
*/
|
*/
|
||||||
public RatPoly subtract(final RatPoly val) {
|
public RatPoly subtract(final RatPoly val) {
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
/*
|
/*
|
||||||
* the degree of the result is the larger of the two degrees (before
|
* the degree of the result is the larger of the two degrees (before
|
||||||
* simplify() at least).
|
* simplify() at least).
|
||||||
*/
|
*/
|
||||||
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
final int nmax = (degree() > val.degree()) ? degree() : val.degree();
|
||||||
for (int n = 0; n <= nmax; n++) {
|
for (int n = 0; n <= nmax; n++) {
|
||||||
Rational coef = at(n).subtract(val.at(n));
|
final Rational coef = at(n).subtract(val.at(n));
|
||||||
resul.set(n, coef);
|
resul.set(n, coef);
|
||||||
}
|
}
|
||||||
resul.simplify();
|
resul.simplify();
|
||||||
@ -525,12 +540,14 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
public RatPoly divide(final Rational val) throws Error {
|
public RatPoly divide(final Rational val) throws Error {
|
||||||
if (val.compareTo(Rational.ZERO) != 0) {
|
if (val.compareTo(Rational.ZERO) != 0) {
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
for (int n = 0; n < a.size(); n++)
|
for (int n = 0; n < a.size(); n++) {
|
||||||
resul.set(n, a.elementAt(n).divide(val));
|
resul.set(n, a.elementAt(n).divide(val));
|
||||||
|
}
|
||||||
return resul;
|
return resul;
|
||||||
} else
|
} else {
|
||||||
throw new ArithmeticException("Cannot divide " + toPString() + " through zero.");
|
throw new ArithmeticException("Cannot divide " + toPString() + " through zero.");
|
||||||
|
}
|
||||||
} /* divide */
|
} /* divide */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -544,8 +561,8 @@ class RatPoly {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public RatPoly divide(final RatPoly val, int nmax) throws Error {
|
public RatPoly divide(final RatPoly val, int nmax) throws Error {
|
||||||
RatPoly num = this;
|
final RatPoly num = this;
|
||||||
RatPoly denom = val;
|
final RatPoly denom = val;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* divide by a common smallest power/degree
|
* divide by a common smallest power/degree
|
||||||
@ -553,11 +570,12 @@ class RatPoly {
|
|||||||
while (num.at(0).compareTo(BigInteger.ZERO) == 0 && denom.at(0).compareTo(BigInteger.ZERO) == 0) {
|
while (num.at(0).compareTo(BigInteger.ZERO) == 0 && denom.at(0).compareTo(BigInteger.ZERO) == 0) {
|
||||||
num.a.remove(0);
|
num.a.remove(0);
|
||||||
denom.a.remove(0);
|
denom.a.remove(0);
|
||||||
if (num.size() <= 1 || denom.size() <= 1)
|
if (num.size() <= 1 || denom.size() <= 1) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
RatPoly resul = new RatPoly();
|
final RatPoly resul = new RatPoly();
|
||||||
/*
|
/*
|
||||||
* todo: If the polynomial division is exact, we could leave
|
* todo: If the polynomial division is exact, we could leave
|
||||||
* the loop earlier, indeed
|
* the loop earlier, indeed
|
||||||
@ -587,20 +605,21 @@ class RatPoly {
|
|||||||
* @since 2012-03-01
|
* @since 2012-03-01
|
||||||
*/
|
*/
|
||||||
public RatPoly[] divideAndRemainder(final RatPoly val) throws Error {
|
public RatPoly[] divideAndRemainder(final RatPoly val) throws Error {
|
||||||
RatPoly[] ret = new RatPoly[2];
|
final RatPoly[] ret = new RatPoly[2];
|
||||||
/*
|
/*
|
||||||
* remove any high-order zeros
|
* remove any high-order zeros
|
||||||
*/
|
*/
|
||||||
RatPoly valSimpl = val.clone();
|
final RatPoly valSimpl = val.clone();
|
||||||
valSimpl.simplify();
|
valSimpl.simplify();
|
||||||
RatPoly thisSimpl = clone();
|
final RatPoly thisSimpl = clone();
|
||||||
thisSimpl.simplify();
|
thisSimpl.simplify();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* catch the case with val equal to zero
|
* catch the case with val equal to zero
|
||||||
*/
|
*/
|
||||||
if (valSimpl.degree() == 0 && valSimpl.a.firstElement().compareTo(Rational.ZERO) == 0)
|
if (valSimpl.degree() == 0 && valSimpl.a.firstElement().compareTo(Rational.ZERO) == 0) {
|
||||||
throw new ArithmeticException("Division through zero polynomial");
|
throw new ArithmeticException("Division through zero polynomial");
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* degree of this smaller than degree of val: remainder is this
|
* degree of this smaller than degree of val: remainder is this
|
||||||
*/
|
*/
|
||||||
@ -628,10 +647,10 @@ class RatPoly {
|
|||||||
/*
|
/*
|
||||||
* any remainder left ?
|
* any remainder left ?
|
||||||
*/
|
*/
|
||||||
if (ret[1].degree() < valSimpl.degree())
|
if (ret[1].degree() < valSimpl.degree()) {
|
||||||
;
|
;
|
||||||
else {
|
} else {
|
||||||
RatPoly rem[] = ret[1].divideAndRemainder(val);
|
final RatPoly rem[] = ret[1].divideAndRemainder(val);
|
||||||
ret[0] = ret[0].add(rem[0]);
|
ret[0] = ret[0].add(rem[0]);
|
||||||
ret[1] = rem[1];
|
ret[1] = rem[1];
|
||||||
}
|
}
|
||||||
@ -651,16 +670,18 @@ class RatPoly {
|
|||||||
public String toString() {
|
public String toString() {
|
||||||
String str = new String();
|
String str = new String();
|
||||||
for (int n = 0; n < a.size(); n++) {
|
for (int n = 0; n < a.size(); n++) {
|
||||||
if (n == 0)
|
if (n == 0) {
|
||||||
str += a.elementAt(n).toString();
|
str += a.elementAt(n).toString();
|
||||||
else
|
} else {
|
||||||
str += "," + a.elementAt(n).toString();
|
str += "," + a.elementAt(n).toString();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* print at least a sole zero
|
* print at least a sole zero
|
||||||
*/
|
*/
|
||||||
if (str.length() == 0)
|
if (str.length() == 0) {
|
||||||
str = "0";
|
str = "0";
|
||||||
|
}
|
||||||
return str;
|
return str;
|
||||||
} /* toString */
|
} /* toString */
|
||||||
|
|
||||||
@ -677,21 +698,24 @@ class RatPoly {
|
|||||||
final BigInteger num = a.elementAt(n).a;
|
final BigInteger num = a.elementAt(n).a;
|
||||||
if (num.compareTo(BigInteger.ZERO) != 0) {
|
if (num.compareTo(BigInteger.ZERO) != 0) {
|
||||||
str += " ";
|
str += " ";
|
||||||
if (num.compareTo(BigInteger.ZERO) > 0)
|
if (num.compareTo(BigInteger.ZERO) > 0) {
|
||||||
str += "+";
|
str += "+";
|
||||||
|
}
|
||||||
str += a.elementAt(n).toString();
|
str += a.elementAt(n).toString();
|
||||||
if (n > 0) {
|
if (n > 0) {
|
||||||
str += "*x";
|
str += "*x";
|
||||||
if (n > 1)
|
if (n > 1) {
|
||||||
str += "^" + n;
|
str += "^" + n;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* print at least a sole zero
|
* print at least a sole zero
|
||||||
*/
|
*/
|
||||||
if (str.length() == 0)
|
if (str.length() == 0) {
|
||||||
str = "0";
|
str = "0";
|
||||||
|
}
|
||||||
return str;
|
return str;
|
||||||
} /* toPString */
|
} /* toPString */
|
||||||
|
|
||||||
@ -703,12 +727,14 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
private void simplify() {
|
private void simplify() {
|
||||||
int n = a.size() - 1;
|
int n = a.size() - 1;
|
||||||
if (n >= 0)
|
if (n >= 0) {
|
||||||
while (a.elementAt(n).compareTo(BigInteger.ZERO) == 0) {
|
while (a.elementAt(n).compareTo(BigInteger.ZERO) == 0) {
|
||||||
a.remove(n);
|
a.remove(n);
|
||||||
if (--n < 0)
|
if (--n < 0) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} /* simplify */
|
} /* simplify */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -718,13 +744,13 @@ class RatPoly {
|
|||||||
* @since 2008-10-26
|
* @since 2008-10-26
|
||||||
*/
|
*/
|
||||||
public RatPoly derive() {
|
public RatPoly derive() {
|
||||||
if (a.size() <= 1)
|
if (a.size() <= 1) {
|
||||||
/*
|
/*
|
||||||
* derivative of the constant is just zero
|
* derivative of the constant is just zero
|
||||||
*/
|
*/
|
||||||
return new RatPoly();
|
return new RatPoly();
|
||||||
else {
|
} else {
|
||||||
RatPoly d = new RatPoly();
|
final RatPoly d = new RatPoly();
|
||||||
for (int i = 1; i <= degree(); i++) {
|
for (int i = 1; i <= degree(); i++) {
|
||||||
final Rational c = a.elementAt(i).multiply(i);
|
final Rational c = a.elementAt(i).multiply(i);
|
||||||
d.set(i - 1, c);
|
d.set(i - 1, c);
|
||||||
@ -742,7 +768,7 @@ class RatPoly {
|
|||||||
* @since 2008-10-26
|
* @since 2008-10-26
|
||||||
*/
|
*/
|
||||||
public RatPoly monic() throws Error {
|
public RatPoly monic() throws Error {
|
||||||
RatPoly m = new RatPoly();
|
final RatPoly m = new RatPoly();
|
||||||
final int d = degree();
|
final int d = degree();
|
||||||
for (int i = 0; i <= d; i++) {
|
for (int i = 0; i <= d; i++) {
|
||||||
final Rational c = a.elementAt(i).divide(a.elementAt(d));
|
final Rational c = a.elementAt(i).divide(a.elementAt(d));
|
||||||
@ -764,7 +790,7 @@ class RatPoly {
|
|||||||
/*
|
/*
|
||||||
* Start with the polynomial 0
|
* Start with the polynomial 0
|
||||||
*/
|
*/
|
||||||
RatPoly r = new RatPoly();
|
final RatPoly r = new RatPoly();
|
||||||
for (int i = 1; i <= maxdeg; i++) {
|
for (int i = 1; i <= maxdeg; i++) {
|
||||||
Rational c = new Rational();
|
Rational c = new Rational();
|
||||||
for (int d = 1; d <= i && d < a.size(); d++) {
|
for (int d = 1; d <= i && d < a.size(); d++) {
|
||||||
@ -792,12 +818,13 @@ class RatPoly {
|
|||||||
/*
|
/*
|
||||||
* Start with the polynomial 0
|
* Start with the polynomial 0
|
||||||
*/
|
*/
|
||||||
RatPoly r = new RatPoly();
|
final RatPoly r = new RatPoly();
|
||||||
for (int i = 1; i <= maxdeg; i++) {
|
for (int i = 1; i <= maxdeg; i++) {
|
||||||
Rational c = new Rational();
|
Rational c = new Rational();
|
||||||
for (int d = 1; d <= i && d < a.size(); d++) {
|
for (int d = 1; d <= i && d < a.size(); d++) {
|
||||||
if (i % d == 0)
|
if (i % d == 0) {
|
||||||
c = c.add(a.elementAt(d));
|
c = c.add(a.elementAt(d));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
r.set(i, c);
|
r.set(i, c);
|
||||||
}
|
}
|
||||||
@ -815,11 +842,12 @@ class RatPoly {
|
|||||||
* @since 2008-10-26
|
* @since 2008-10-26
|
||||||
*/
|
*/
|
||||||
public RatPoly binomialT(int maxdeg) {
|
public RatPoly binomialT(int maxdeg) {
|
||||||
RatPoly r = new RatPoly();
|
final RatPoly r = new RatPoly();
|
||||||
for (int i = 0; i <= maxdeg; i++) {
|
for (int i = 0; i <= maxdeg; i++) {
|
||||||
Rational c = new Rational(0, 1);
|
Rational c = new Rational(0, 1);
|
||||||
for (int j = 0; j <= i && j < a.size(); j++)
|
for (int j = 0; j <= i && j < a.size(); j++) {
|
||||||
c = c.add(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
c = c.add(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
||||||
|
}
|
||||||
r.set(i, c);
|
r.set(i, c);
|
||||||
}
|
}
|
||||||
r.simplify();
|
r.simplify();
|
||||||
@ -836,14 +864,16 @@ class RatPoly {
|
|||||||
* @since 2008-10-26
|
* @since 2008-10-26
|
||||||
*/
|
*/
|
||||||
public RatPoly binomialTInv(int maxdeg) {
|
public RatPoly binomialTInv(int maxdeg) {
|
||||||
RatPoly r = new RatPoly();
|
final RatPoly r = new RatPoly();
|
||||||
for (int i = 0; i <= maxdeg; i++) {
|
for (int i = 0; i <= maxdeg; i++) {
|
||||||
Rational c = new Rational(0, 1);
|
Rational c = new Rational(0, 1);
|
||||||
for (int j = 0; j <= i && j < a.size(); j++)
|
for (int j = 0; j <= i && j < a.size(); j++) {
|
||||||
if ((j + i) % 2 != 0)
|
if ((j + i) % 2 != 0) {
|
||||||
c = c.subtract(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
c = c.subtract(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
||||||
else
|
} else {
|
||||||
c = c.add(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
c = c.add(a.elementAt(j).multiply(BigIntegerMath.binomial(i, j)));
|
||||||
|
}
|
||||||
|
}
|
||||||
r.set(i, c);
|
r.set(i, c);
|
||||||
}
|
}
|
||||||
r.simplify();
|
r.simplify();
|
||||||
@ -865,9 +895,10 @@ class RatPoly {
|
|||||||
* @since 2008-10-26
|
* @since 2008-10-26
|
||||||
*/
|
*/
|
||||||
public RatPoly trunc(int newdeg) {
|
public RatPoly trunc(int newdeg) {
|
||||||
RatPoly t = new RatPoly();
|
final RatPoly t = new RatPoly();
|
||||||
for (int i = 0; i <= newdeg; i++)
|
for (int i = 0; i <= newdeg; i++) {
|
||||||
t.set(i, at(i));
|
t.set(i, at(i));
|
||||||
|
}
|
||||||
t.simplify();
|
t.simplify();
|
||||||
return t;
|
return t;
|
||||||
} /* trunc */
|
} /* trunc */
|
||||||
@ -883,10 +914,10 @@ class RatPoly {
|
|||||||
* @since 2008-10-26
|
* @since 2008-10-26
|
||||||
*/
|
*/
|
||||||
public Vector<BigComplex> roots(int digits) throws Error {
|
public Vector<BigComplex> roots(int digits) throws Error {
|
||||||
RatPoly mon = monic();
|
final RatPoly mon = monic();
|
||||||
|
|
||||||
Random rand = new Random();
|
final Random rand = new Random();
|
||||||
MathContext mc = new MathContext(digits + 3, RoundingMode.DOWN);
|
final MathContext mc = new MathContext(digits + 3, RoundingMode.DOWN);
|
||||||
|
|
||||||
Vector<BigComplex> res = new Vector<>();
|
Vector<BigComplex> res = new Vector<>();
|
||||||
|
|
||||||
@ -894,9 +925,10 @@ class RatPoly {
|
|||||||
double randRad = 0.;
|
double randRad = 0.;
|
||||||
for (int i = 0; i <= d; i++) {
|
for (int i = 0; i <= d; i++) {
|
||||||
/* scale coefficient at maximum degree */
|
/* scale coefficient at maximum degree */
|
||||||
double absi = Math.abs(mon.at(i).doubleValue());
|
final double absi = Math.abs(mon.at(i).doubleValue());
|
||||||
if (absi > randRad)
|
if (absi > randRad) {
|
||||||
randRad = absi;
|
randRad = absi;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
randRad += 1.0;
|
randRad += 1.0;
|
||||||
|
|
||||||
@ -904,8 +936,8 @@ class RatPoly {
|
|||||||
* initial values randomly in radius 1+randRad
|
* initial values randomly in radius 1+randRad
|
||||||
*/
|
*/
|
||||||
for (int i = 0; i < d; i++) {
|
for (int i = 0; i < d; i++) {
|
||||||
double rad = randRad * rand.nextDouble();
|
final double rad = randRad * rand.nextDouble();
|
||||||
double phi = 2.0 * 3.14159 * rand.nextDouble();
|
final double phi = 2.0 * 3.14159 * rand.nextDouble();
|
||||||
res.add(i, new BigComplex(rad * Math.cos(phi), rad * Math.sin(phi)));
|
res.add(i, new BigComplex(rad * Math.cos(phi), rad * Math.sin(phi)));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -918,7 +950,7 @@ class RatPoly {
|
|||||||
for (; !convr;)// ORIGINAL LINE: for(int itr =0 ; ! convr ; itr++)
|
for (; !convr;)// ORIGINAL LINE: for(int itr =0 ; ! convr ; itr++)
|
||||||
{
|
{
|
||||||
convr = true;
|
convr = true;
|
||||||
Vector<BigComplex> resPlus = new Vector<>();
|
final Vector<BigComplex> resPlus = new Vector<>();
|
||||||
for (int v = 0; v < d; v++) {
|
for (int v = 0; v < d; v++) {
|
||||||
/*
|
/*
|
||||||
* evaluate f(x)/(x-root1)/(x-root2)/... (x-rootdegr), Newton
|
* evaluate f(x)/(x-root1)/(x-root2)/... (x-rootdegr), Newton
|
||||||
@ -927,19 +959,22 @@ class RatPoly {
|
|||||||
BigComplex thisx = res.elementAt(v);
|
BigComplex thisx = res.elementAt(v);
|
||||||
BigComplex nv = mon.valueOf(thisx, mc);
|
BigComplex nv = mon.valueOf(thisx, mc);
|
||||||
for (int j = 0; j < d; j++) {
|
for (int j = 0; j < d; j++) {
|
||||||
if (j != v)
|
if (j != v) {
|
||||||
nv = nv.divide(thisx.subtract(res.elementAt(j)), mc);
|
nv = nv.divide(thisx.subtract(res.elementAt(j)), mc);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* is this value converged ? */
|
/* is this value converged ? */
|
||||||
if (nv.abs(mc).doubleValue() > thisx.abs(mc).doubleValue() * Math.pow(10.0, -digits))
|
if (nv.abs(mc).doubleValue() > thisx.abs(mc).doubleValue() * Math.pow(10.0, -digits)) {
|
||||||
convr = false;
|
convr = false;
|
||||||
|
}
|
||||||
|
|
||||||
thisx = thisx.subtract(nv);
|
thisx = thisx.subtract(nv);
|
||||||
|
|
||||||
/* If unstable, start over */
|
/* If unstable, start over */
|
||||||
if (thisx.abs(MathContext.DECIMAL32).doubleValue() > randRad)
|
if (thisx.abs(MathContext.DECIMAL32).doubleValue() > randRad) {
|
||||||
return roots(digits);
|
return roots(digits);
|
||||||
|
}
|
||||||
|
|
||||||
resPlus.add(thisx);
|
resPlus.add(thisx);
|
||||||
}
|
}
|
||||||
@ -959,9 +994,9 @@ class RatPoly {
|
|||||||
*/
|
*/
|
||||||
public Vector<BigInteger> iroots() {
|
public Vector<BigInteger> iroots() {
|
||||||
/* The vector of the roots */
|
/* The vector of the roots */
|
||||||
Vector<BigInteger> res = new Vector<>();
|
final Vector<BigInteger> res = new Vector<>();
|
||||||
|
|
||||||
int lowd = ldegree();
|
final int lowd = ldegree();
|
||||||
if (lowd == 0 && a.elementAt(0).compareTo(BigInteger.ZERO) == 0) {
|
if (lowd == 0 && a.elementAt(0).compareTo(BigInteger.ZERO) == 0) {
|
||||||
/*
|
/*
|
||||||
* Case of polynomial identical to zero:
|
* Case of polynomial identical to zero:
|
||||||
@ -977,28 +1012,29 @@ class RatPoly {
|
|||||||
* start with denominator of first non-zero coefficient.
|
* start with denominator of first non-zero coefficient.
|
||||||
*/
|
*/
|
||||||
BigInteger lcmDeno = a.elementAt(lowd).b;
|
BigInteger lcmDeno = a.elementAt(lowd).b;
|
||||||
for (int i = lowd + 1; i < degree(); i++)
|
for (int i = lowd + 1; i < degree(); i++) {
|
||||||
lcmDeno = BigIntegerMath.lcm(lcmDeno, a.elementAt(i).b);
|
lcmDeno = BigIntegerMath.lcm(lcmDeno, a.elementAt(i).b);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* and eventually get the integer polynomial by ignoring the
|
* and eventually get the integer polynomial by ignoring the
|
||||||
* denominators
|
* denominators
|
||||||
*/
|
*/
|
||||||
Vector<BigInteger> ipo = new Vector<>();
|
final Vector<BigInteger> ipo = new Vector<>();
|
||||||
for (int i = 0; i < a.size(); i++) {
|
for (int i = 0; i < a.size(); i++) {
|
||||||
BigInteger d = a.elementAt(i).a.multiply(lcmDeno).divide(a.elementAt(i).b);
|
final BigInteger d = a.elementAt(i).a.multiply(lcmDeno).divide(a.elementAt(i).b);
|
||||||
ipo.add(d);
|
ipo.add(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
BigIntegerPoly p = new BigIntegerPoly(ipo);
|
final BigIntegerPoly p = new BigIntegerPoly(ipo);
|
||||||
/*
|
/*
|
||||||
* collect the integer roots (multiple roots only once). Since we
|
* collect the integer roots (multiple roots only once). Since we
|
||||||
* removed the zero already above, cand does not contain zeros.
|
* removed the zero already above, cand does not contain zeros.
|
||||||
*/
|
*/
|
||||||
Vector<BigInteger> cand = p.iroots();
|
final Vector<BigInteger> cand = p.iroots();
|
||||||
for (int i = 0; i < cand.size(); i++) {
|
for (int i = 0; i < cand.size(); i++) {
|
||||||
final BigInteger r = cand.elementAt(i);
|
final BigInteger r = cand.elementAt(i);
|
||||||
int deg = p.rootDeg(r);
|
final int deg = p.rootDeg(r);
|
||||||
res.add(r);
|
res.add(r);
|
||||||
res.add(new BigInteger("" + deg));
|
res.add(new BigInteger("" + deg));
|
||||||
}
|
}
|
||||||
|
@ -133,7 +133,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* does not yet test for a denominator equal to zero
|
* does not yet test for a denominator equal to zero
|
||||||
*/
|
*/
|
||||||
public Rational(String str, int radix) {
|
public Rational(String str, int radix) {
|
||||||
int hasslah = str.indexOf("/");
|
final int hasslah = str.indexOf("/");
|
||||||
if (hasslah == -1) {
|
if (hasslah == -1) {
|
||||||
a = new BigInteger(str, radix);
|
a = new BigInteger(str, radix);
|
||||||
b = new BigInteger("1", radix);
|
b = new BigInteger("1", radix);
|
||||||
@ -159,8 +159,8 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* protected access means this does not work return new
|
* protected access means this does not work return new
|
||||||
* Rational(a.clone(), b.clone()) ;
|
* Rational(a.clone(), b.clone()) ;
|
||||||
*/
|
*/
|
||||||
BigInteger aclon = new BigInteger("" + a);
|
final BigInteger aclon = new BigInteger("" + a);
|
||||||
BigInteger bclon = new BigInteger("" + b);
|
final BigInteger bclon = new BigInteger("" + b);
|
||||||
return new Rational(aclon, bclon);
|
return new Rational(aclon, bclon);
|
||||||
} /* Rational.clone */
|
} /* Rational.clone */
|
||||||
|
|
||||||
@ -172,8 +172,8 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return the product of this with the val.
|
* @return the product of this with the val.
|
||||||
*/
|
*/
|
||||||
public Rational multiply(final Rational val) {
|
public Rational multiply(final Rational val) {
|
||||||
BigInteger num = a.multiply(val.a);
|
final BigInteger num = a.multiply(val.a);
|
||||||
BigInteger deno = b.multiply(val.b);
|
final BigInteger deno = b.multiply(val.b);
|
||||||
/*
|
/*
|
||||||
* Normalization to an coprime format will be done inside the ctor() and
|
* Normalization to an coprime format will be done inside the ctor() and
|
||||||
* is not duplicated here.
|
* is not duplicated here.
|
||||||
@ -189,7 +189,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return the product of this with the value.
|
* @return the product of this with the value.
|
||||||
*/
|
*/
|
||||||
public Rational multiply(final BigInteger val) {
|
public Rational multiply(final BigInteger val) {
|
||||||
Rational val2 = new Rational(val, BigInteger.ONE);
|
final Rational val2 = new Rational(val, BigInteger.ONE);
|
||||||
return (multiply(val2));
|
return (multiply(val2));
|
||||||
} /* Rational.multiply */
|
} /* Rational.multiply */
|
||||||
|
|
||||||
@ -201,7 +201,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return the product of this with the value.
|
* @return the product of this with the value.
|
||||||
*/
|
*/
|
||||||
public Rational multiply(final int val) {
|
public Rational multiply(final int val) {
|
||||||
BigInteger tmp = new BigInteger("" + val);
|
final BigInteger tmp = new BigInteger("" + val);
|
||||||
return multiply(tmp);
|
return multiply(tmp);
|
||||||
} /* Rational.multiply */
|
} /* Rational.multiply */
|
||||||
|
|
||||||
@ -214,15 +214,17 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* exponent is 0, the value 1 is returned.
|
* exponent is 0, the value 1 is returned.
|
||||||
*/
|
*/
|
||||||
public Rational pow(int exponent) {
|
public Rational pow(int exponent) {
|
||||||
if (exponent == 0)
|
if (exponent == 0) {
|
||||||
return new Rational(1, 1);
|
return new Rational(1, 1);
|
||||||
|
}
|
||||||
|
|
||||||
BigInteger num = a.pow(Math.abs(exponent));
|
final BigInteger num = a.pow(Math.abs(exponent));
|
||||||
BigInteger deno = b.pow(Math.abs(exponent));
|
final BigInteger deno = b.pow(Math.abs(exponent));
|
||||||
if (exponent > 0)
|
if (exponent > 0) {
|
||||||
return (new Rational(num, deno));
|
return (new Rational(num, deno));
|
||||||
else
|
} else {
|
||||||
return (new Rational(deno, num));
|
return (new Rational(deno, num));
|
||||||
|
}
|
||||||
} /* Rational.pow */
|
} /* Rational.pow */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -237,10 +239,12 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
*/
|
*/
|
||||||
public Rational pow(BigInteger exponent) throws Error {
|
public Rational pow(BigInteger exponent) throws Error {
|
||||||
/* test for overflow */
|
/* test for overflow */
|
||||||
if (exponent.compareTo(MAX_INT) == 1)
|
if (exponent.compareTo(MAX_INT) == 1) {
|
||||||
throw new Error(Errors.NUMBER_TOO_LARGE);
|
throw new Error(Errors.NUMBER_TOO_LARGE);
|
||||||
if (exponent.compareTo(MIN_INT) == -1)
|
}
|
||||||
|
if (exponent.compareTo(MIN_INT) == -1) {
|
||||||
throw new Error(Errors.NUMBER_TOO_SMALL);
|
throw new Error(Errors.NUMBER_TOO_SMALL);
|
||||||
|
}
|
||||||
|
|
||||||
/* promote to the simpler interface above */
|
/* promote to the simpler interface above */
|
||||||
return pow(exponent.intValue());
|
return pow(exponent.intValue());
|
||||||
@ -259,15 +263,18 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
*/
|
*/
|
||||||
public Rational root(BigInteger r) throws Error {
|
public Rational root(BigInteger r) throws Error {
|
||||||
/* test for overflow */
|
/* test for overflow */
|
||||||
if (r.compareTo(MAX_INT) == 1)
|
if (r.compareTo(MAX_INT) == 1) {
|
||||||
throw new Error(Errors.NUMBER_TOO_LARGE);
|
throw new Error(Errors.NUMBER_TOO_LARGE);
|
||||||
if (r.compareTo(MIN_INT) == -1)
|
}
|
||||||
|
if (r.compareTo(MIN_INT) == -1) {
|
||||||
throw new Error(Errors.NUMBER_TOO_SMALL);
|
throw new Error(Errors.NUMBER_TOO_SMALL);
|
||||||
|
}
|
||||||
|
|
||||||
int rthroot = r.intValue();
|
final int rthroot = r.intValue();
|
||||||
/* cannot pull root of a negative value with even-valued root */
|
/* cannot pull root of a negative value with even-valued root */
|
||||||
if (compareTo(ZERO) == -1 && (rthroot % 2) == 0)
|
if (compareTo(ZERO) == -1 && (rthroot % 2) == 0) {
|
||||||
throw new Error(Errors.NEGATIVE_PARAMETER);
|
throw new Error(Errors.NEGATIVE_PARAMETER);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* extract a sign such that we calculate |n|^(1/r), still r carrying any
|
* extract a sign such that we calculate |n|^(1/r), still r carrying any
|
||||||
@ -278,13 +285,14 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
/*
|
/*
|
||||||
* delegate the main work to ifactor#root()
|
* delegate the main work to ifactor#root()
|
||||||
*/
|
*/
|
||||||
Ifactor num = new Ifactor(a.abs());
|
final Ifactor num = new Ifactor(a.abs());
|
||||||
Ifactor deno = new Ifactor(b);
|
final Ifactor deno = new Ifactor(b);
|
||||||
final Rational resul = num.root(rthroot).divide(deno.root(rthroot));
|
final Rational resul = num.root(rthroot).divide(deno.root(rthroot));
|
||||||
if (flipsign)
|
if (flipsign) {
|
||||||
return resul.negate();
|
return resul.negate();
|
||||||
else
|
} else {
|
||||||
return resul;
|
return resul;
|
||||||
|
}
|
||||||
} /* Rational.root */
|
} /* Rational.root */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -298,14 +306,15 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2009-05-18
|
* @since 2009-05-18
|
||||||
*/
|
*/
|
||||||
public Rational pow(Rational exponent) throws Error {
|
public Rational pow(Rational exponent) throws Error {
|
||||||
if (exponent.a.compareTo(BigInteger.ZERO) == 0)
|
if (exponent.a.compareTo(BigInteger.ZERO) == 0) {
|
||||||
return new Rational(1, 1);
|
return new Rational(1, 1);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* calculate (a/b)^(exponent.a/exponent.b) as
|
* calculate (a/b)^(exponent.a/exponent.b) as
|
||||||
* ((a/b)^exponent.a)^(1/exponent.b) = tmp^(1/exponent.b)
|
* ((a/b)^exponent.a)^(1/exponent.b) = tmp^(1/exponent.b)
|
||||||
*/
|
*/
|
||||||
Rational tmp = pow(exponent.a);
|
final Rational tmp = pow(exponent.a);
|
||||||
return tmp.root(exponent.b);
|
return tmp.root(exponent.b);
|
||||||
} /* Rational.pow */
|
} /* Rational.pow */
|
||||||
|
|
||||||
@ -318,10 +327,11 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public Rational divide(final Rational val) throws Error {
|
public Rational divide(final Rational val) throws Error {
|
||||||
if (val.compareTo(Rational.ZERO) == 0)
|
if (val.compareTo(Rational.ZERO) == 0) {
|
||||||
throw new Error(Errors.DIVISION_BY_ZERO);
|
throw new Error(Errors.DIVISION_BY_ZERO);
|
||||||
BigInteger num = a.multiply(val.b);
|
}
|
||||||
BigInteger deno = b.multiply(val.a);
|
final BigInteger num = a.multiply(val.b);
|
||||||
|
final BigInteger deno = b.multiply(val.a);
|
||||||
/*
|
/*
|
||||||
* Reduction to a coprime format is done inside the ctor, and not
|
* Reduction to a coprime format is done inside the ctor, and not
|
||||||
* repeated here.
|
* repeated here.
|
||||||
@ -338,9 +348,10 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public Rational divide(BigInteger val) throws Error {
|
public Rational divide(BigInteger val) throws Error {
|
||||||
if (val.compareTo(BigInteger.ZERO) == 0)
|
if (val.compareTo(BigInteger.ZERO) == 0) {
|
||||||
throw new Error(Errors.DIVISION_BY_ZERO);
|
throw new Error(Errors.DIVISION_BY_ZERO);
|
||||||
Rational val2 = new Rational(val, BigInteger.ONE);
|
}
|
||||||
|
final Rational val2 = new Rational(val, BigInteger.ONE);
|
||||||
return (divide(val2));
|
return (divide(val2));
|
||||||
} /* Rational.divide */
|
} /* Rational.divide */
|
||||||
|
|
||||||
@ -353,9 +364,10 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public Rational divide(int val) throws Error {
|
public Rational divide(int val) throws Error {
|
||||||
if (val == 0)
|
if (val == 0) {
|
||||||
throw new Error(Errors.DIVISION_BY_ZERO);
|
throw new Error(Errors.DIVISION_BY_ZERO);
|
||||||
Rational val2 = new Rational(val, 1);
|
}
|
||||||
|
final Rational val2 = new Rational(val, 1);
|
||||||
return (divide(val2));
|
return (divide(val2));
|
||||||
} /* Rational.divide */
|
} /* Rational.divide */
|
||||||
|
|
||||||
@ -367,8 +379,8 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return this+val.
|
* @return this+val.
|
||||||
*/
|
*/
|
||||||
public Rational add(Rational val) {
|
public Rational add(Rational val) {
|
||||||
BigInteger num = a.multiply(val.b).add(b.multiply(val.a));
|
final BigInteger num = a.multiply(val.b).add(b.multiply(val.a));
|
||||||
BigInteger deno = b.multiply(val.b);
|
final BigInteger deno = b.multiply(val.b);
|
||||||
return (new Rational(num, deno));
|
return (new Rational(num, deno));
|
||||||
} /* Rational.add */
|
} /* Rational.add */
|
||||||
|
|
||||||
@ -380,7 +392,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return this+val.
|
* @return this+val.
|
||||||
*/
|
*/
|
||||||
public Rational add(BigInteger val) {
|
public Rational add(BigInteger val) {
|
||||||
Rational val2 = new Rational(val, BigInteger.ONE);
|
final Rational val2 = new Rational(val, BigInteger.ONE);
|
||||||
return (add(val2));
|
return (add(val2));
|
||||||
} /* Rational.add */
|
} /* Rational.add */
|
||||||
|
|
||||||
@ -393,7 +405,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since May 26 2010
|
* @since May 26 2010
|
||||||
*/
|
*/
|
||||||
public Rational add(int val) {
|
public Rational add(int val) {
|
||||||
BigInteger val2 = a.add(b.multiply(new BigInteger("" + val)));
|
final BigInteger val2 = a.add(b.multiply(new BigInteger("" + val)));
|
||||||
return new Rational(val2, b);
|
return new Rational(val2, b);
|
||||||
} /* Rational.add */
|
} /* Rational.add */
|
||||||
|
|
||||||
@ -414,7 +426,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return this - val.
|
* @return this - val.
|
||||||
*/
|
*/
|
||||||
public Rational subtract(Rational val) {
|
public Rational subtract(Rational val) {
|
||||||
Rational val2 = val.negate();
|
final Rational val2 = val.negate();
|
||||||
return (add(val2));
|
return (add(val2));
|
||||||
} /* Rational.subtract */
|
} /* Rational.subtract */
|
||||||
|
|
||||||
@ -426,7 +438,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return this - val.
|
* @return this - val.
|
||||||
*/
|
*/
|
||||||
public Rational subtract(BigInteger val) {
|
public Rational subtract(BigInteger val) {
|
||||||
Rational val2 = new Rational(val, BigInteger.ONE);
|
final Rational val2 = new Rational(val, BigInteger.ONE);
|
||||||
return (subtract(val2));
|
return (subtract(val2));
|
||||||
} /* Rational.subtract */
|
} /* Rational.subtract */
|
||||||
|
|
||||||
@ -438,7 +450,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @return this - val.
|
* @return this - val.
|
||||||
*/
|
*/
|
||||||
public Rational subtract(int val) {
|
public Rational subtract(int val) {
|
||||||
Rational val2 = new Rational(val, 1);
|
final Rational val2 = new Rational(val, 1);
|
||||||
return (subtract(val2));
|
return (subtract(val2));
|
||||||
} /* Rational.subtract */
|
} /* Rational.subtract */
|
||||||
|
|
||||||
@ -455,8 +467,9 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public static Rational binomial(Rational n, BigInteger m) throws Error {
|
public static Rational binomial(Rational n, BigInteger m) throws Error {
|
||||||
if (m.compareTo(BigInteger.ZERO) == 0)
|
if (m.compareTo(BigInteger.ZERO) == 0) {
|
||||||
return Rational.ONE;
|
return Rational.ONE;
|
||||||
|
}
|
||||||
Rational bin = n;
|
Rational bin = n;
|
||||||
for (BigInteger i = new BigInteger("2"); i.compareTo(m) != 1; i = i.add(BigInteger.ONE)) {
|
for (BigInteger i = new BigInteger("2"); i.compareTo(m) != 1; i = i.add(BigInteger.ONE)) {
|
||||||
bin = bin.multiply(n.subtract(i.subtract(BigInteger.ONE))).divide(i);
|
bin = bin.multiply(n.subtract(i.subtract(BigInteger.ONE))).divide(i);
|
||||||
@ -477,8 +490,9 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public static Rational binomial(Rational n, int m) throws Error {
|
public static Rational binomial(Rational n, int m) throws Error {
|
||||||
if (m == 0)
|
if (m == 0) {
|
||||||
return Rational.ONE;
|
return Rational.ONE;
|
||||||
|
}
|
||||||
Rational bin = n;
|
Rational bin = n;
|
||||||
for (int i = 2; i <= m; i++) {
|
for (int i = 2; i <= m; i++) {
|
||||||
bin = bin.multiply(n.subtract(i - 1)).divide(i);
|
bin = bin.multiply(n.subtract(i - 1)).divide(i);
|
||||||
@ -499,13 +513,14 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
public static Rational hankelSymb(Rational n, int k) throws Error {
|
public static Rational hankelSymb(Rational n, int k) throws Error {
|
||||||
if (k == 0)
|
if (k == 0) {
|
||||||
return Rational.ONE;
|
return Rational.ONE;
|
||||||
else if (k < 0)
|
} else if (k < 0) {
|
||||||
throw new Error(Errors.NEGATIVE_PARAMETER);
|
throw new Error(Errors.NEGATIVE_PARAMETER);
|
||||||
|
}
|
||||||
Rational nkhalf = n.subtract(k).add(Rational.HALF);
|
Rational nkhalf = n.subtract(k).add(Rational.HALF);
|
||||||
nkhalf = nkhalf.Pochhammer(2 * k);
|
nkhalf = nkhalf.Pochhammer(2 * k);
|
||||||
Factorial f = new Factorial();
|
final Factorial f = new Factorial();
|
||||||
return nkhalf.divide(f.at(k));
|
return nkhalf.divide(f.at(k));
|
||||||
} /* Rational.binomial */
|
} /* Rational.binomial */
|
||||||
|
|
||||||
@ -545,12 +560,13 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
/*
|
/*
|
||||||
* is already integer: return the numerator
|
* is already integer: return the numerator
|
||||||
*/
|
*/
|
||||||
if (b.compareTo(BigInteger.ONE) == 0)
|
if (b.compareTo(BigInteger.ONE) == 0) {
|
||||||
return a;
|
return a;
|
||||||
else if (a.compareTo(BigInteger.ZERO) > 0)
|
} else if (a.compareTo(BigInteger.ZERO) > 0) {
|
||||||
return a.divide(b);
|
return a.divide(b);
|
||||||
else
|
} else {
|
||||||
return a.divide(b).subtract(BigInteger.ONE);
|
return a.divide(b).subtract(BigInteger.ONE);
|
||||||
|
}
|
||||||
} /* Rational.floor */
|
} /* Rational.floor */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -563,12 +579,13 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
/*
|
/*
|
||||||
* is already integer: return the numerator
|
* is already integer: return the numerator
|
||||||
*/
|
*/
|
||||||
if (b.compareTo(BigInteger.ONE) == 0)
|
if (b.compareTo(BigInteger.ONE) == 0) {
|
||||||
return a;
|
return a;
|
||||||
else if (a.compareTo(BigInteger.ZERO) > 0)
|
} else if (a.compareTo(BigInteger.ZERO) > 0) {
|
||||||
return a.divide(b).add(BigInteger.ONE);
|
return a.divide(b).add(BigInteger.ONE);
|
||||||
else
|
} else {
|
||||||
return a.divide(b);
|
return a.divide(b);
|
||||||
|
}
|
||||||
} /* Rational.ceil */
|
} /* Rational.ceil */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -580,10 +597,11 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
/*
|
/*
|
||||||
* is already integer: return the numerator
|
* is already integer: return the numerator
|
||||||
*/
|
*/
|
||||||
if (b.compareTo(BigInteger.ONE) == 0)
|
if (b.compareTo(BigInteger.ONE) == 0) {
|
||||||
return a;
|
return a;
|
||||||
else
|
} else {
|
||||||
return a.divide(b);
|
return a.divide(b);
|
||||||
|
}
|
||||||
} /* Rational.trunc */
|
} /* Rational.trunc */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -626,10 +644,11 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
if (b.compareTo(BigInteger.ONE) != 0)
|
if (b.compareTo(BigInteger.ONE) != 0) {
|
||||||
return (a.toString() + "/" + b.toString());
|
return (a.toString() + "/" + b.toString());
|
||||||
else
|
} else {
|
||||||
return a.toString();
|
return a.toString();
|
||||||
|
}
|
||||||
} /* Rational.toString */
|
} /* Rational.toString */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -644,7 +663,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* separate invocation a.doubleValue() or b.doubleValue(), we divide
|
* separate invocation a.doubleValue() or b.doubleValue(), we divide
|
||||||
* first in a BigDecimal environment and convert the result.
|
* first in a BigDecimal environment and convert the result.
|
||||||
*/
|
*/
|
||||||
BigDecimal adivb = (new BigDecimal(a)).divide(new BigDecimal(b), MathContext.DECIMAL128);
|
final BigDecimal adivb = (new BigDecimal(a)).divide(new BigDecimal(b), MathContext.DECIMAL128);
|
||||||
return adivb.doubleValue();
|
return adivb.doubleValue();
|
||||||
} /* Rational.doubleValue */
|
} /* Rational.doubleValue */
|
||||||
|
|
||||||
@ -655,7 +674,7 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2009-08-06
|
* @since 2009-08-06
|
||||||
*/
|
*/
|
||||||
public float floatValue() {
|
public float floatValue() {
|
||||||
BigDecimal adivb = (new BigDecimal(a)).divide(new BigDecimal(b), MathContext.DECIMAL128);
|
final BigDecimal adivb = (new BigDecimal(a)).divide(new BigDecimal(b), MathContext.DECIMAL128);
|
||||||
return adivb.floatValue();
|
return adivb.floatValue();
|
||||||
} /* Rational.floatValue */
|
} /* Rational.floatValue */
|
||||||
|
|
||||||
@ -672,8 +691,8 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
/*
|
/*
|
||||||
* numerator and denominator individually rephrased
|
* numerator and denominator individually rephrased
|
||||||
*/
|
*/
|
||||||
BigDecimal n = new BigDecimal(a);
|
final BigDecimal n = new BigDecimal(a);
|
||||||
BigDecimal d = new BigDecimal(b);
|
final BigDecimal d = new BigDecimal(b);
|
||||||
/*
|
/*
|
||||||
* the problem with n.divide(d,mc) is that the apparent precision might
|
* the problem with n.divide(d,mc) is that the apparent precision might
|
||||||
* be smaller than what is set by mc if the value has a precise
|
* be smaller than what is set by mc if the value has a precise
|
||||||
@ -692,11 +711,12 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
*/
|
*/
|
||||||
public String toFString(int digits) {
|
public String toFString(int digits) {
|
||||||
if (b.compareTo(BigInteger.ONE) != 0) {
|
if (b.compareTo(BigInteger.ONE) != 0) {
|
||||||
MathContext mc = new MathContext(digits, RoundingMode.DOWN);
|
final MathContext mc = new MathContext(digits, RoundingMode.DOWN);
|
||||||
BigDecimal f = (new BigDecimal(a)).divide(new BigDecimal(b), mc);
|
final BigDecimal f = (new BigDecimal(a)).divide(new BigDecimal(b), mc);
|
||||||
return (f.toString());
|
return (f.toString());
|
||||||
} else
|
} else {
|
||||||
return a.toString();
|
return a.toString();
|
||||||
|
}
|
||||||
} /* Rational.toFString */
|
} /* Rational.toFString */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -708,10 +728,11 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2008-10-19
|
* @since 2008-10-19
|
||||||
*/
|
*/
|
||||||
public Rational max(final Rational val) {
|
public Rational max(final Rational val) {
|
||||||
if (compareTo(val) > 0)
|
if (compareTo(val) > 0) {
|
||||||
return this;
|
return this;
|
||||||
else
|
} else {
|
||||||
return val;
|
return val;
|
||||||
|
}
|
||||||
} /* Rational.max */
|
} /* Rational.max */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -723,10 +744,11 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2008-10-19
|
* @since 2008-10-19
|
||||||
*/
|
*/
|
||||||
public Rational min(final Rational val) {
|
public Rational min(final Rational val) {
|
||||||
if (compareTo(val) < 0)
|
if (compareTo(val) < 0) {
|
||||||
return this;
|
return this;
|
||||||
else
|
} else {
|
||||||
return val;
|
return val;
|
||||||
|
}
|
||||||
} /* Rational.min */
|
} /* Rational.min */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -738,18 +760,19 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2008-10-25
|
* @since 2008-10-25
|
||||||
*/
|
*/
|
||||||
public Rational Pochhammer(final BigInteger n) {
|
public Rational Pochhammer(final BigInteger n) {
|
||||||
if (n.compareTo(BigInteger.ZERO) < 0)
|
if (n.compareTo(BigInteger.ZERO) < 0) {
|
||||||
return null;
|
return null;
|
||||||
else if (n.compareTo(BigInteger.ZERO) == 0)
|
} else if (n.compareTo(BigInteger.ZERO) == 0) {
|
||||||
return Rational.ONE;
|
return Rational.ONE;
|
||||||
else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* initialize results with the current value
|
* initialize results with the current value
|
||||||
*/
|
*/
|
||||||
Rational res = new Rational(a, b);
|
Rational res = new Rational(a, b);
|
||||||
BigInteger i = BigInteger.ONE;
|
BigInteger i = BigInteger.ONE;
|
||||||
for (; i.compareTo(n) < 0; i = i.add(BigInteger.ONE))
|
for (; i.compareTo(n) < 0; i = i.add(BigInteger.ONE)) {
|
||||||
res = res.multiply(add(i));
|
res = res.multiply(add(i));
|
||||||
|
}
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
} /* Rational.pochhammer */
|
} /* Rational.pochhammer */
|
||||||
@ -784,8 +807,9 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2010-05-26
|
* @since 2010-05-26
|
||||||
*/
|
*/
|
||||||
public boolean isInteger() {
|
public boolean isInteger() {
|
||||||
if (!isBigInteger())
|
if (!isBigInteger()) {
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
return (a.compareTo(MAX_INT) <= 0 && a.compareTo(MIN_INT) >= 0);
|
return (a.compareTo(MAX_INT) <= 0 && a.compareTo(MIN_INT) >= 0);
|
||||||
} /* Rational.isInteger */
|
} /* Rational.isInteger */
|
||||||
|
|
||||||
@ -797,8 +821,9 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2011-02-13
|
* @since 2011-02-13
|
||||||
*/
|
*/
|
||||||
int intValue() throws Error {
|
int intValue() throws Error {
|
||||||
if (!isInteger())
|
if (!isInteger()) {
|
||||||
throw new Error(Errors.CONVERSION_ERROR);
|
throw new Error(Errors.CONVERSION_ERROR);
|
||||||
|
}
|
||||||
return a.intValue();
|
return a.intValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -810,8 +835,9 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
* @since 2012-03-02
|
* @since 2012-03-02
|
||||||
*/
|
*/
|
||||||
BigInteger BigIntegerValue() throws Error {
|
BigInteger BigIntegerValue() throws Error {
|
||||||
if (!isBigInteger())
|
if (!isBigInteger()) {
|
||||||
throw new Error(Errors.CONVERSION_ERROR);
|
throw new Error(Errors.CONVERSION_ERROR);
|
||||||
|
}
|
||||||
return a;
|
return a;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -845,8 +871,9 @@ public class Rational implements Cloneable, Comparable<Rational> {
|
|||||||
*/
|
*/
|
||||||
static public BigInteger lcmDenom(final Rational[] vals) {
|
static public BigInteger lcmDenom(final Rational[] vals) {
|
||||||
BigInteger l = BigInteger.ONE;
|
BigInteger l = BigInteger.ONE;
|
||||||
for (int v = 0; v < vals.length; v++)
|
for (final Rational val : vals) {
|
||||||
l = BigIntegerMath.lcm(l, vals[v].b);
|
l = BigIntegerMath.lcm(l, val.b);
|
||||||
|
}
|
||||||
return l;
|
return l;
|
||||||
} /* Rational.lcmDenom */
|
} /* Rational.lcmDenom */
|
||||||
|
|
||||||
|
@ -37,43 +37,45 @@ public class Wigner3j {
|
|||||||
static public void main(String args[]) throws Error {
|
static public void main(String args[]) throws Error {
|
||||||
if (args[0].compareTo("6j") == 0) {
|
if (args[0].compareTo("6j") == 0) {
|
||||||
try {
|
try {
|
||||||
String m1 = "6";
|
final String m1 = "6";
|
||||||
String t1 = "1 2 -3 -1 5 6";
|
final String t1 = "1 2 -3 -1 5 6";
|
||||||
String t2 = "4 -5 3 -4 -2 -6";
|
final String t2 = "4 -5 3 -4 -2 -6";
|
||||||
String j = "";
|
String j = "";
|
||||||
for (int i = 1; i <= 6; i++)
|
for (int i = 1; i <= 6; i++) {
|
||||||
j += args[i] + " ";
|
j += args[i] + " ";
|
||||||
BigSurdVec w = wigner3j(m1, t1, t2, j);
|
}
|
||||||
|
final BigSurdVec w = wigner3j(m1, t1, t2, j);
|
||||||
System.out.println(w.toString());
|
System.out.println(w.toString());
|
||||||
} catch (Exception e) {
|
} catch (final Exception e) {
|
||||||
System.out.println(e.getMessage());
|
System.out.println(e.getMessage());
|
||||||
}
|
}
|
||||||
} else if (args[0].compareTo("9j") == 0) {
|
} else if (args[0].compareTo("9j") == 0) {
|
||||||
try {
|
try {
|
||||||
String m1 = "9";
|
final String m1 = "9";
|
||||||
String t1 = "1 3 2 4 6 5 7 9 8";
|
final String t1 = "1 3 2 4 6 5 7 9 8";
|
||||||
String t2 = "2 8 5 6 3 9 7 4 1";
|
final String t2 = "2 8 5 6 3 9 7 4 1";
|
||||||
String j = "";
|
String j = "";
|
||||||
for (int i = 1; i <= 9; i++)
|
for (int i = 1; i <= 9; i++) {
|
||||||
j += args[i] + " ";
|
j += args[i] + " ";
|
||||||
BigSurdVec w = wigner3j(m1, t1, t2, j);
|
}
|
||||||
|
final BigSurdVec w = wigner3j(m1, t1, t2, j);
|
||||||
System.out.println(w.toString());
|
System.out.println(w.toString());
|
||||||
} catch (Exception e) {
|
} catch (final Exception e) {
|
||||||
System.out.println(e.getMessage());
|
System.out.println(e.getMessage());
|
||||||
}
|
}
|
||||||
} else if (args[0].compareTo("3jm") == 0) {
|
} else if (args[0].compareTo("3jm") == 0) {
|
||||||
int j1 = (new Integer(args[1])).intValue();
|
final int j1 = (new Integer(args[1])).intValue();
|
||||||
int j2 = (new Integer(args[2])).intValue();
|
final int j2 = (new Integer(args[2])).intValue();
|
||||||
int j3 = (new Integer(args[3])).intValue();
|
final int j3 = (new Integer(args[3])).intValue();
|
||||||
int m1 = (new Integer(args[4])).intValue();
|
final int m1 = (new Integer(args[4])).intValue();
|
||||||
int m2 = (new Integer(args[5])).intValue();
|
final int m2 = (new Integer(args[5])).intValue();
|
||||||
int m3 = (new Integer(args[6])).intValue();
|
final int m3 = (new Integer(args[6])).intValue();
|
||||||
try {
|
try {
|
||||||
BigSurd w = wigner3jm(j1, j2, j3, m1, m2, m3);
|
BigSurd w = wigner3jm(j1, j2, j3, m1, m2, m3);
|
||||||
System.out.println(w.toString());
|
System.out.println(w.toString());
|
||||||
w = w.multiply(new BigSurd(j3 + 1, 1));
|
w = w.multiply(new BigSurd(j3 + 1, 1));
|
||||||
System.out.println("CG factor sqrt" + (j3 + 1) + "sign " + ((j2 - j2 - m3) / 2) + " " + w.toString());
|
System.out.println("CG factor sqrt" + (j3 + 1) + "sign " + ((j2 - j2 - m3) / 2) + " " + w.toString());
|
||||||
} catch (Exception e) {
|
} catch (final Exception e) {
|
||||||
System.out.println(e.getMessage());
|
System.out.println(e.getMessage());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -108,12 +110,12 @@ public class Wigner3j {
|
|||||||
* @throws Error
|
* @throws Error
|
||||||
*/
|
*/
|
||||||
static public BigSurd wigner3jm(int j1, int j2, int j3, int m1, int m2, int m3) throws Error {
|
static public BigSurd wigner3jm(int j1, int j2, int j3, int m1, int m2, int m3) throws Error {
|
||||||
Rational J1 = new Rational(j1, 2);
|
final Rational J1 = new Rational(j1, 2);
|
||||||
Rational J2 = new Rational(j2, 2);
|
final Rational J2 = new Rational(j2, 2);
|
||||||
Rational J3 = new Rational(j3, 2);
|
final Rational J3 = new Rational(j3, 2);
|
||||||
Rational M1 = new Rational(m1, 2);
|
final Rational M1 = new Rational(m1, 2);
|
||||||
Rational M2 = new Rational(m2, 2);
|
final Rational M2 = new Rational(m2, 2);
|
||||||
Rational M3 = new Rational(m3, 2);
|
final Rational M3 = new Rational(m3, 2);
|
||||||
return wigner3jm(J1, J2, J3, M1, M2, M3);
|
return wigner3jm(J1, J2, J3, M1, M2, M3);
|
||||||
} /* wigner3jm */
|
} /* wigner3jm */
|
||||||
|
|
||||||
@ -148,7 +150,7 @@ public class Wigner3j {
|
|||||||
* The rest of the line is ignored.
|
* The rest of the line is ignored.
|
||||||
*/
|
*/
|
||||||
Scanner s = new Scanner(m1);
|
Scanner s = new Scanner(m1);
|
||||||
int m = s.nextInt();
|
final int m = s.nextInt();
|
||||||
if (m % 3 != 0) {
|
if (m % 3 != 0) {
|
||||||
s.close();
|
s.close();
|
||||||
throw new IllegalArgumentException("Angular momenta " + m + " not a multiple of three.");
|
throw new IllegalArgumentException("Angular momenta " + m + " not a multiple of three.");
|
||||||
@ -158,8 +160,8 @@ public class Wigner3j {
|
|||||||
* Scan the numbers in the line "j". Excess numbers beyond what has been
|
* Scan the numbers in the line "j". Excess numbers beyond what has been
|
||||||
* announced in the "m" line are ignored.
|
* announced in the "m" line are ignored.
|
||||||
*/
|
*/
|
||||||
int[] jvec = new int[m];
|
final int[] jvec = new int[m];
|
||||||
int[] tvec = new int[2 * m];
|
final int[] tvec = new int[2 * m];
|
||||||
|
|
||||||
s.close();
|
s.close();
|
||||||
|
|
||||||
@ -183,14 +185,16 @@ public class Wigner3j {
|
|||||||
*/
|
*/
|
||||||
s = new Scanner(t1);
|
s = new Scanner(t1);
|
||||||
int ti = 0;
|
int ti = 0;
|
||||||
while (s.hasNextInt())
|
while (s.hasNextInt()) {
|
||||||
tvec[ti++] = s.nextInt();
|
tvec[ti++] = s.nextInt();
|
||||||
|
}
|
||||||
|
|
||||||
s.close();
|
s.close();
|
||||||
|
|
||||||
s = new Scanner(t2);
|
s = new Scanner(t2);
|
||||||
while (s.hasNextInt())
|
while (s.hasNextInt()) {
|
||||||
tvec[ti++] = s.nextInt();
|
tvec[ti++] = s.nextInt();
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Basic sanity checks. All indices in the first two lines address a
|
* Basic sanity checks. All indices in the first two lines address a
|
||||||
@ -205,18 +209,19 @@ public class Wigner3j {
|
|||||||
throw new IllegalArgumentException("triad-count " + ti + " not twice j-count " + ji);
|
throw new IllegalArgumentException("triad-count " + ti + " not twice j-count " + ji);
|
||||||
}
|
}
|
||||||
|
|
||||||
int[] jfreq = new int[m];
|
final int[] jfreq = new int[m];
|
||||||
for (ji = 0; ji < jfreq.length; ji++)
|
for (ji = 0; ji < jfreq.length; ji++) {
|
||||||
jfreq[ji] = 0;
|
jfreq[ji] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* maintain a 0-based index which shows where the j-value has its first
|
* maintain a 0-based index which shows where the j-value has its first
|
||||||
* and second occurrence in the flattened list of triads.
|
* and second occurrence in the flattened list of triads.
|
||||||
*/
|
*/
|
||||||
int[][] jhash = new int[m][2];
|
final int[][] jhash = new int[m][2];
|
||||||
|
|
||||||
for (ti = 0; ti < 2 * m; ti++) {
|
for (ti = 0; ti < 2 * m; ti++) {
|
||||||
int t = tvec[ti];
|
final int t = tvec[ti];
|
||||||
if (t == 0 || Math.abs(t) > jvec.length) {
|
if (t == 0 || Math.abs(t) > jvec.length) {
|
||||||
s.close();
|
s.close();
|
||||||
throw new IllegalArgumentException("Triad index " + t + " out of bounds");
|
throw new IllegalArgumentException("Triad index " + t + " out of bounds");
|
||||||
@ -233,7 +238,7 @@ public class Wigner3j {
|
|||||||
* Move on from the 2j+1 values of the input to the j-values. Subtract
|
* Move on from the 2j+1 values of the input to the j-values. Subtract
|
||||||
* one and divide through 2.
|
* one and divide through 2.
|
||||||
*/
|
*/
|
||||||
Rational[] J = new Rational[jvec.length];
|
final Rational[] J = new Rational[jvec.length];
|
||||||
for (ji = 0; ji < jvec.length; ji++) {
|
for (ji = 0; ji < jvec.length; ji++) {
|
||||||
J[ji] = new Rational(jvec[ji] - 1, 2);
|
J[ji] = new Rational(jvec[ji] - 1, 2);
|
||||||
}
|
}
|
||||||
@ -242,14 +247,15 @@ public class Wigner3j {
|
|||||||
* Convert the 1-based indices to 0-based indices, loosing the sign
|
* Convert the 1-based indices to 0-based indices, loosing the sign
|
||||||
* information.
|
* information.
|
||||||
*/
|
*/
|
||||||
int[] triadidx = new int[tvec.length];
|
final int[] triadidx = new int[tvec.length];
|
||||||
for (ti = 0; ti < tvec.length; ti++)
|
for (ti = 0; ti < tvec.length; ti++) {
|
||||||
triadidx[ti] = Math.abs(tvec[ti]) - 1;
|
triadidx[ti] = Math.abs(tvec[ti]) - 1;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The M-values are all null (undetermined) at the start.
|
* The M-values are all null (undetermined) at the start.
|
||||||
*/
|
*/
|
||||||
Rational[] M = new Rational[J.length];
|
final Rational[] M = new Rational[J.length];
|
||||||
s.close();
|
s.close();
|
||||||
return wigner3j(tvec, J, M, triadidx);
|
return wigner3j(tvec, J, M, triadidx);
|
||||||
} /* wigner3j */
|
} /* wigner3j */
|
||||||
@ -286,10 +292,12 @@ public class Wigner3j {
|
|||||||
*/
|
*/
|
||||||
for (int t = 0; t < triadidx.length; t += 3) {
|
for (int t = 0; t < triadidx.length; t += 3) {
|
||||||
/* Ensure |J[t]-J[t+1]| <= J[t+2] <= J[t]+J[t+1] */
|
/* Ensure |J[t]-J[t+1]| <= J[t+2] <= J[t]+J[t+1] */
|
||||||
if (J[triadidx[t]].subtract(J[triadidx[t + 1]]).abs().compareTo(J[triadidx[t + 2]]) > 0)
|
if (J[triadidx[t]].subtract(J[triadidx[t + 1]]).abs().compareTo(J[triadidx[t + 2]]) > 0) {
|
||||||
return res;
|
return res;
|
||||||
if (J[triadidx[t]].add(J[triadidx[t + 1]]).compareTo(J[triadidx[t + 2]]) < 0)
|
}
|
||||||
|
if (J[triadidx[t]].add(J[triadidx[t + 1]]).compareTo(J[triadidx[t + 2]]) < 0) {
|
||||||
return res;
|
return res;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -310,14 +318,14 @@ public class Wigner3j {
|
|||||||
* others values are set in the triad. or it is still to
|
* others values are set in the triad. or it is still to
|
||||||
* maintain its own explicit loop.
|
* maintain its own explicit loop.
|
||||||
*/
|
*/
|
||||||
int triadn = i / 3;
|
final int triadn = i / 3;
|
||||||
int triadr = i % 3;
|
final int triadr = i % 3;
|
||||||
/*
|
/*
|
||||||
* the neighbors in the triad have indices triadn*3+ (tiradr+1)
|
* the neighbors in the triad have indices triadn*3+ (tiradr+1)
|
||||||
* mod 3 and triadn*3+(triadr+2) mod3
|
* mod 3 and triadn*3+(triadr+2) mod3
|
||||||
*/
|
*/
|
||||||
int nei1 = 3 * triadn + (triadr + 1) % 3;
|
final int nei1 = 3 * triadn + (triadr + 1) % 3;
|
||||||
int nei2 = 3 * triadn + (triadr + 2) % 3;
|
final int nei2 = 3 * triadn + (triadr + 2) % 3;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* found a candidate for which the two other values are already
|
* found a candidate for which the two other values are already
|
||||||
@ -331,11 +339,13 @@ public class Wigner3j {
|
|||||||
* rough work load estimator: basically (2J1+1)*(2J2+1)
|
* rough work load estimator: basically (2J1+1)*(2J2+1)
|
||||||
*/
|
*/
|
||||||
Rational wt = J[triadidx[i]].multiply(2).add(1);
|
Rational wt = J[triadidx[i]].multiply(2).add(1);
|
||||||
if (M[triadidx[nei1]] == null)
|
if (M[triadidx[nei1]] == null) {
|
||||||
wt = wt.multiply(J[triadidx[nei1]].multiply(2).add(1));
|
wt = wt.multiply(J[triadidx[nei1]].multiply(2).add(1));
|
||||||
if (M[triadidx[nei2]] == null)
|
}
|
||||||
|
if (M[triadidx[nei2]] == null) {
|
||||||
wt = wt.multiply(J[triadidx[nei2]].multiply(2).add(1));
|
wt = wt.multiply(J[triadidx[nei2]].multiply(2).add(1));
|
||||||
int thiswt = wt.intValue();
|
}
|
||||||
|
final int thiswt = wt.intValue();
|
||||||
if (freeM < 0 || thiswt < freeMrank) {
|
if (freeM < 0 || thiswt < freeMrank) {
|
||||||
freeM = i;
|
freeM = i;
|
||||||
freeMrank = thiswt;
|
freeMrank = thiswt;
|
||||||
@ -349,24 +359,26 @@ public class Wigner3j {
|
|||||||
* found an m-value which has not yet been summed over.
|
* found an m-value which has not yet been summed over.
|
||||||
*/
|
*/
|
||||||
if (M[triadidx[freeM]] == null) {
|
if (M[triadidx[freeM]] == null) {
|
||||||
Rational[] childM = new Rational[M.length];
|
final Rational[] childM = new Rational[M.length];
|
||||||
for (int ji = 0; ji < M.length; ji++)
|
for (int ji = 0; ji < M.length; ji++) {
|
||||||
if (M[ji] != null)
|
if (M[ji] != null) {
|
||||||
childM[ji] = M[ji];
|
childM[ji] = M[ji];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* two cases: value is fixed implicitly because already two
|
* two cases: value is fixed implicitly because already two
|
||||||
* others values are set in the triad. or it is still to
|
* others values are set in the triad. or it is still to
|
||||||
* maintain its own explicit loop.
|
* maintain its own explicit loop.
|
||||||
*/
|
*/
|
||||||
int triadn = freeM / 3;
|
final int triadn = freeM / 3;
|
||||||
int triadr = freeM % 3;
|
final int triadr = freeM % 3;
|
||||||
/*
|
/*
|
||||||
* the neighbors in the triad have indices triadn*3+ (triadr+1)
|
* the neighbors in the triad have indices triadn*3+ (triadr+1)
|
||||||
* mod 3 and triadn*3+(triadr+2) mod3
|
* mod 3 and triadn*3+(triadr+2) mod3
|
||||||
*/
|
*/
|
||||||
int nei1 = 3 * triadn + (triadr + 1) % 3;
|
final int nei1 = 3 * triadn + (triadr + 1) % 3;
|
||||||
int nei2 = 3 * triadn + (triadr + 2) % 3;
|
final int nei2 = 3 * triadn + (triadr + 2) % 3;
|
||||||
if (M[triadidx[nei1]] == null || M[triadidx[nei2]] == null) {
|
if (M[triadidx[nei1]] == null || M[triadidx[nei2]] == null) {
|
||||||
/*
|
/*
|
||||||
* The J-value is J[triadidx[freeM]]. Loop from -J to +J,
|
* The J-value is J[triadidx[freeM]]. Loop from -J to +J,
|
||||||
@ -390,12 +402,14 @@ public class Wigner3j {
|
|||||||
* negate if these are the second occurrences of the J in
|
* negate if these are the second occurrences of the J in
|
||||||
* the triads
|
* the triads
|
||||||
*/
|
*/
|
||||||
if (tvec[nei1] < 0)
|
if (tvec[nei1] < 0) {
|
||||||
m1 = m1.negate();
|
m1 = m1.negate();
|
||||||
if (tvec[nei2] < 0)
|
}
|
||||||
|
if (tvec[nei2] < 0) {
|
||||||
m2 = m2.negate();
|
m2 = m2.negate();
|
||||||
|
}
|
||||||
/* m3 = -(m1+m2) */
|
/* m3 = -(m1+m2) */
|
||||||
Rational newm = tvec[freeM] > 0 ? m1.add(m2).negate() : m1.add(m2);
|
final Rational newm = tvec[freeM] > 0 ? m1.add(m2).negate() : m1.add(m2);
|
||||||
/*
|
/*
|
||||||
* No contribution if the m-value enforced by the other two
|
* No contribution if the m-value enforced by the other two
|
||||||
* entries is outside the range -|J|..|J| enforced by its
|
* entries is outside the range -|J|..|J| enforced by its
|
||||||
@ -429,34 +443,40 @@ public class Wigner3j {
|
|||||||
* negate if these are associated with in-flowing vectors in the
|
* negate if these are associated with in-flowing vectors in the
|
||||||
* triads
|
* triads
|
||||||
*/
|
*/
|
||||||
if (tvec[ji] < 0)
|
if (tvec[ji] < 0) {
|
||||||
m1 = m1.negate();
|
m1 = m1.negate();
|
||||||
if (tvec[ji + 1] < 0)
|
}
|
||||||
|
if (tvec[ji + 1] < 0) {
|
||||||
m2 = m2.negate();
|
m2 = m2.negate();
|
||||||
if (tvec[ji + 2] < 0)
|
}
|
||||||
|
if (tvec[ji + 2] < 0) {
|
||||||
m3 = m3.negate();
|
m3 = m3.negate();
|
||||||
|
}
|
||||||
res = res.multiply(wigner3jm(J[triadidx[ji]], J[triadidx[ji + 1]], J[triadidx[ji + 2]], m1, m2, m3));
|
res = res.multiply(wigner3jm(J[triadidx[ji]], J[triadidx[ji + 1]], J[triadidx[ji + 2]], m1, m2, m3));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* if a partial product yields zero, the total product is zero, too,
|
* if a partial product yields zero, the total product is zero, too,
|
||||||
* and offers an early exit.
|
* and offers an early exit.
|
||||||
*/
|
*/
|
||||||
if (res.signum() == 0)
|
if (res.signum() == 0) {
|
||||||
return BigSurdVec.ZERO;
|
return BigSurdVec.ZERO;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* The overal sign is product_{J-Mpairs} (-1)^(J-M). This is an integer
|
* The overal sign is product_{J-Mpairs} (-1)^(J-M). This is an integer
|
||||||
* because all the J-M are integer.
|
* because all the J-M are integer.
|
||||||
*/
|
*/
|
||||||
Rational sig = new Rational();
|
Rational sig = new Rational();
|
||||||
for (int ji = 0; ji < J.length; ji++)
|
for (int ji = 0; ji < J.length; ji++) {
|
||||||
sig = sig.add(J[ji]).subtract(M[ji]);
|
sig = sig.add(J[ji]).subtract(M[ji]);
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* sign depends on the sum being even or odd. We assume that "sig" is
|
* sign depends on the sum being even or odd. We assume that "sig" is
|
||||||
* integer and look only at the numerator
|
* integer and look only at the numerator
|
||||||
*/
|
*/
|
||||||
if (sig.a.abs().testBit(0))
|
if (sig.a.abs().testBit(0)) {
|
||||||
res = res.negate();
|
res = res.negate();
|
||||||
|
}
|
||||||
return res;
|
return res;
|
||||||
} /* wigner3j */
|
} /* wigner3j */
|
||||||
|
|
||||||
@ -487,36 +507,42 @@ public class Wigner3j {
|
|||||||
/*
|
/*
|
||||||
* Check that m1+m2+m3 = 0
|
* Check that m1+m2+m3 = 0
|
||||||
*/
|
*/
|
||||||
if (m1.add(m2).add(m3).signum() != 0)
|
if (m1.add(m2).add(m3).signum() != 0) {
|
||||||
return BigSurd.ZERO;
|
return BigSurd.ZERO;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Check that j1+j2+j3 is integer
|
* Check that j1+j2+j3 is integer
|
||||||
*/
|
*/
|
||||||
if (j1.add(j2).add(j3).isBigInteger() == false)
|
if (j1.add(j2).add(j3).isBigInteger() == false) {
|
||||||
return BigSurd.ZERO;
|
return BigSurd.ZERO;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Check that |j1-j2|<=j3 <= |j1+j2|
|
* Check that |j1-j2|<=j3 <= |j1+j2|
|
||||||
*/
|
*/
|
||||||
Rational j1m2 = j1.subtract(j2);
|
final Rational j1m2 = j1.subtract(j2);
|
||||||
if (j1m2.abs().compareTo(j3) > 0)
|
if (j1m2.abs().compareTo(j3) > 0) {
|
||||||
return BigSurd.ZERO;
|
return BigSurd.ZERO;
|
||||||
Rational j1p2 = j1.add(j2);
|
}
|
||||||
if (j1p2.abs().compareTo(j3) < 0)
|
final Rational j1p2 = j1.add(j2);
|
||||||
|
if (j1p2.abs().compareTo(j3) < 0) {
|
||||||
return BigSurd.ZERO;
|
return BigSurd.ZERO;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Check that |m_i| <= j_i
|
* Check that |m_i| <= j_i
|
||||||
*/
|
*/
|
||||||
if (m1.abs().compareTo(j1) > 0 || m2.abs().compareTo(j2) > 0 || m3.abs().compareTo(j3) > 0)
|
if (m1.abs().compareTo(j1) > 0 || m2.abs().compareTo(j2) > 0 || m3.abs().compareTo(j3) > 0) {
|
||||||
return BigSurd.ZERO;
|
return BigSurd.ZERO;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Check that m_i-j_i are integer.
|
* Check that m_i-j_i are integer.
|
||||||
*/
|
*/
|
||||||
if (!m1.subtract(j1).isBigInteger() || !m2.subtract(j2).isBigInteger() || !m3.subtract(j3).isBigInteger())
|
if (!m1.subtract(j1).isBigInteger() || !m2.subtract(j2).isBigInteger() || !m3.subtract(j3).isBigInteger()) {
|
||||||
return BigSurd.ZERO;
|
return BigSurd.ZERO;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* (-)^(j1-j2-m3)*delta(-m3,m1+m2)*sqrt[ (j3+j1-j2)! (j3-j1+j2)!
|
* (-)^(j1-j2-m3)*delta(-m3,m1+m2)*sqrt[ (j3+j1-j2)! (j3-j1+j2)!
|
||||||
@ -548,28 +574,31 @@ public class Wigner3j {
|
|||||||
jj1m2k += k;
|
jj1m2k += k;
|
||||||
}
|
}
|
||||||
|
|
||||||
Factorial f = new Factorial();
|
final Factorial f = new Factorial();
|
||||||
Rational sumk = new Rational();
|
Rational sumk = new Rational();
|
||||||
while (true) {
|
while (true) {
|
||||||
BigInteger d = f.at(k).multiply(f.at(j1j2jk)).multiply(f.at(j1m1k)).multiply(f.at(j2m2k)).multiply(f.at(jj2m1k)).multiply(f.at(jj1m2k));
|
final BigInteger d = f.at(k).multiply(f.at(j1j2jk)).multiply(f.at(j1m1k)).multiply(f.at(j2m2k)).multiply(f.at(jj2m1k)).multiply(f.at(jj1m2k));
|
||||||
if (k % 2 == 0)
|
if (k % 2 == 0) {
|
||||||
sumk = sumk.add(new Rational(BigInteger.ONE, d));
|
sumk = sumk.add(new Rational(BigInteger.ONE, d));
|
||||||
else
|
} else {
|
||||||
sumk = sumk.subtract(new Rational(BigInteger.ONE, d));
|
sumk = sumk.subtract(new Rational(BigInteger.ONE, d));
|
||||||
|
}
|
||||||
j1j2jk--;
|
j1j2jk--;
|
||||||
j1m1k--;
|
j1m1k--;
|
||||||
j2m2k--;
|
j2m2k--;
|
||||||
jj2m1k++;
|
jj2m1k++;
|
||||||
jj1m2k++;
|
jj1m2k++;
|
||||||
if (j1j2jk < 0 || j1m1k < 0 || j2m2k < 0)
|
if (j1j2jk < 0 || j1m1k < 0 || j2m2k < 0) {
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
k++;
|
k++;
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* sign factor (-1)^(j1-j2-m3)
|
* sign factor (-1)^(j1-j2-m3)
|
||||||
*/
|
*/
|
||||||
if (j1m2.subtract(m3).intValue() % 2 != 0)
|
if (j1m2.subtract(m3).intValue() % 2 != 0) {
|
||||||
sumk = sumk.negate();
|
sumk = sumk.negate();
|
||||||
|
}
|
||||||
|
|
||||||
k = j1m2.add(j3).intValue();
|
k = j1m2.add(j3).intValue();
|
||||||
BigInteger s = f.at(k);
|
BigInteger s = f.at(k);
|
||||||
@ -591,7 +620,7 @@ public class Wigner3j {
|
|||||||
s = s.multiply(f.at(k));
|
s = s.multiply(f.at(k));
|
||||||
k = j1p2.add(j3).intValue();
|
k = j1p2.add(j3).intValue();
|
||||||
k++;
|
k++;
|
||||||
Rational disc = new Rational(s, f.at(k));
|
final Rational disc = new Rational(s, f.at(k));
|
||||||
return new BigSurd(sumk, disc);
|
return new BigSurd(sumk, disc);
|
||||||
} /* wigner3jm */
|
} /* wigner3jm */
|
||||||
|
|
||||||
|
@ -79,12 +79,12 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
searJ.setLayoutOrientation(JList.HORIZONTAL_WRAP);
|
searJ.setLayoutOrientation(JList.HORIZONTAL_WRAP);
|
||||||
searJ.addListSelectionListener(this);
|
searJ.addListSelectionListener(this);
|
||||||
|
|
||||||
Font defFont = new Font("Monospaced", Font.PLAIN, 11);
|
final Font defFont = new Font("Monospaced", Font.PLAIN, 11);
|
||||||
|
|
||||||
fram.setBackground(new Color(250, 250, 250));
|
fram.setBackground(new Color(250, 250, 250));
|
||||||
fram.setForeground(new Color(0, 0, 0));
|
fram.setForeground(new Color(0, 0, 0));
|
||||||
Color fg = new Color(0, 200, 0);
|
final Color fg = new Color(0, 200, 0);
|
||||||
Color bg = new Color(10, 10, 10);
|
final Color bg = new Color(10, 10, 10);
|
||||||
|
|
||||||
gridbag = new GridBagLayout();
|
gridbag = new GridBagLayout();
|
||||||
fram.setLayout(gridbag);
|
fram.setLayout(gridbag);
|
||||||
@ -138,8 +138,8 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
* @since 2010-08-27
|
* @since 2010-08-27
|
||||||
*/
|
*/
|
||||||
public void compute() throws Error {
|
public void compute() throws Error {
|
||||||
String tr = inpGtria.getText();
|
final String tr = inpGtria.getText();
|
||||||
String[] trias = new String[4];
|
final String[] trias = new String[4];
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Read the trias configuration from inpGtria into trias[0..2], skipping
|
* Read the trias configuration from inpGtria into trias[0..2], skipping
|
||||||
@ -149,9 +149,10 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
for (int l = 0; l < 3;) {
|
for (int l = 0; l < 3;) {
|
||||||
try {
|
try {
|
||||||
trias[l] = s.nextLine().trim();
|
trias[l] = s.nextLine().trim();
|
||||||
if (!trias[l].startsWith("#"))
|
if (!trias[l].startsWith("#")) {
|
||||||
l++;
|
l++;
|
||||||
} catch (Exception e) {
|
}
|
||||||
|
} catch (final Exception e) {
|
||||||
s.close();
|
s.close();
|
||||||
outG.setText("ERROR: less than 3 lines in the triad definition");
|
outG.setText("ERROR: less than 3 lines in the triad definition");
|
||||||
return;
|
return;
|
||||||
@ -163,28 +164,28 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
/*
|
/*
|
||||||
* Read the J values from inpGjval into trias[3] in a loop
|
* Read the J values from inpGjval into trias[3] in a loop
|
||||||
*/
|
*/
|
||||||
String j = inpGjval.getText();
|
final String j = inpGjval.getText();
|
||||||
s = new Scanner(j);
|
s = new Scanner(j);
|
||||||
while (true) {
|
while (true) {
|
||||||
try {
|
try {
|
||||||
trias[3] = s.nextLine().trim();
|
trias[3] = s.nextLine().trim();
|
||||||
} catch (Exception e) {
|
} catch (final Exception e) {
|
||||||
s.close();
|
s.close();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (!trias[3].startsWith("#")) {
|
if (!trias[3].startsWith("#")) {
|
||||||
try {
|
try {
|
||||||
BigSurdVec w = Wigner3j.wigner3j(trias[0], trias[1], trias[2], trias[3]);
|
final BigSurdVec w = Wigner3j.wigner3j(trias[0], trias[1], trias[2], trias[3]);
|
||||||
outG.append(w.toString() + " = " + w.doubleValue());
|
outG.append(w.toString() + " = " + w.doubleValue());
|
||||||
} catch (Exception e) {
|
} catch (final Exception e) {
|
||||||
outG.append(e.toString());
|
outG.append(e.toString());
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
outG.append(" # J = ");
|
outG.append(" # J = ");
|
||||||
Scanner num = new Scanner(trias[3]);
|
final Scanner num = new Scanner(trias[3]);
|
||||||
while (num.hasNextInt()) {
|
while (num.hasNextInt()) {
|
||||||
int twoj1 = num.nextInt();
|
final int twoj1 = num.nextInt();
|
||||||
Rational jfrac = new Rational(twoj1 - 1, 2);
|
final Rational jfrac = new Rational(twoj1 - 1, 2);
|
||||||
outG.append(jfrac.toString() + " ");
|
outG.append(jfrac.toString() + " ");
|
||||||
}
|
}
|
||||||
outG.append("\n");
|
outG.append("\n");
|
||||||
@ -202,7 +203,7 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void actionPerformed(ActionEvent e) {
|
public void actionPerformed(ActionEvent e) {
|
||||||
String lin = e.getActionCommand();
|
final String lin = e.getActionCommand();
|
||||||
/*
|
/*
|
||||||
* debugging System.out.println("Ac"+e.paramString()) ;
|
* debugging System.out.println("Ac"+e.paramString()) ;
|
||||||
* System.out.println(lin) ;
|
* System.out.println(lin) ;
|
||||||
@ -211,7 +212,7 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
outG.setText("");
|
outG.setText("");
|
||||||
try {
|
try {
|
||||||
compute();
|
compute();
|
||||||
} catch (Error e1) {
|
} catch (final Error e1) {
|
||||||
// TODO Auto-generated catch block
|
// TODO Auto-generated catch block
|
||||||
e1.printStackTrace();
|
e1.printStackTrace();
|
||||||
}
|
}
|
||||||
@ -327,7 +328,7 @@ public class Wigner3jGUI implements ActionListener, ListSelectionListener {
|
|||||||
* @author Richard J. Mathar
|
* @author Richard J. Mathar
|
||||||
*/
|
*/
|
||||||
public static void main(String[] args) {
|
public static void main(String[] args) {
|
||||||
Wigner3jGUI g = new Wigner3jGUI();
|
final Wigner3jGUI g = new Wigner3jGUI();
|
||||||
g.init();
|
g.init();
|
||||||
} /* main */
|
} /* main */
|
||||||
|
|
||||||
|
@ -16,26 +16,26 @@ public class BMPFile extends Component {
|
|||||||
// --- Private variable declaration
|
// --- Private variable declaration
|
||||||
// --- Bitmap file header
|
// --- Bitmap file header
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
private byte bitmapFileHeader[] = new byte[14];
|
private final byte bitmapFileHeader[] = new byte[14];
|
||||||
private byte bfType[] = { 'B', 'M' };
|
private final byte bfType[] = { 'B', 'M' };
|
||||||
private int bfSize = 0;
|
private int bfSize = 0;
|
||||||
private int bfReserved1 = 0;
|
private final int bfReserved1 = 0;
|
||||||
private int bfReserved2 = 0;
|
private final int bfReserved2 = 0;
|
||||||
private int bfOffBits = BITMAPFILEHEADER_SIZE + BITMAPINFOHEADER_SIZE;
|
private final int bfOffBits = BITMAPFILEHEADER_SIZE + BITMAPINFOHEADER_SIZE;
|
||||||
// --- Bitmap info header
|
// --- Bitmap info header
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
private byte bitmapInfoHeader[] = new byte[40];
|
private final byte bitmapInfoHeader[] = new byte[40];
|
||||||
private int biSize = BITMAPINFOHEADER_SIZE;
|
private final int biSize = BITMAPINFOHEADER_SIZE;
|
||||||
private int biWidth = 0;
|
private int biWidth = 0;
|
||||||
private int biHeight = 0;
|
private int biHeight = 0;
|
||||||
private int biPlanes = 1;
|
private final int biPlanes = 1;
|
||||||
private int biBitCount = 24;
|
private final int biBitCount = 24;
|
||||||
private int biCompression = 0;
|
private final int biCompression = 0;
|
||||||
private int biSizeImage = 0x030000;
|
private int biSizeImage = 0x030000;
|
||||||
private int biXPelsPerMeter = 0x0;
|
private final int biXPelsPerMeter = 0x0;
|
||||||
private int biYPelsPerMeter = 0x0;
|
private final int biYPelsPerMeter = 0x0;
|
||||||
private int biClrUsed = 0;
|
private final int biClrUsed = 0;
|
||||||
private int biClrImportant = 0;
|
private final int biClrImportant = 0;
|
||||||
// --- Bitmap raw data
|
// --- Bitmap raw data
|
||||||
private int bitmap[];
|
private int bitmap[];
|
||||||
// --- File section
|
// --- File section
|
||||||
@ -49,7 +49,7 @@ public class BMPFile extends Component {
|
|||||||
fo = new FileOutputStream(parFilename);
|
fo = new FileOutputStream(parFilename);
|
||||||
save(parImage, parWidth, parHeight);
|
save(parImage, parWidth, parHeight);
|
||||||
fo.close();
|
fo.close();
|
||||||
} catch (Exception saveEx) {
|
} catch (final Exception saveEx) {
|
||||||
saveEx.printStackTrace();
|
saveEx.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -68,7 +68,7 @@ public class BMPFile extends Component {
|
|||||||
writeBitmapFileHeader();
|
writeBitmapFileHeader();
|
||||||
writeBitmapInfoHeader();
|
writeBitmapInfoHeader();
|
||||||
writeBitmap();
|
writeBitmap();
|
||||||
} catch (Exception saveEx) {
|
} catch (final Exception saveEx) {
|
||||||
saveEx.printStackTrace();
|
saveEx.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -81,10 +81,10 @@ public class BMPFile extends Component {
|
|||||||
private boolean convertImage(Image parImage, int parWidth, int parHeight) {
|
private boolean convertImage(Image parImage, int parWidth, int parHeight) {
|
||||||
int pad;
|
int pad;
|
||||||
bitmap = new int[parWidth * parHeight];
|
bitmap = new int[parWidth * parHeight];
|
||||||
PixelGrabber pg = new PixelGrabber(parImage, 0, 0, parWidth, parHeight, bitmap, 0, parWidth);
|
final PixelGrabber pg = new PixelGrabber(parImage, 0, 0, parWidth, parHeight, bitmap, 0, parWidth);
|
||||||
try {
|
try {
|
||||||
pg.grabPixels();
|
pg.grabPixels();
|
||||||
} catch (InterruptedException e) {
|
} catch (final InterruptedException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
return (false);
|
return (false);
|
||||||
}
|
}
|
||||||
@ -113,11 +113,13 @@ public class BMPFile extends Component {
|
|||||||
int lastRowIndex;
|
int lastRowIndex;
|
||||||
int pad;
|
int pad;
|
||||||
int padCount;
|
int padCount;
|
||||||
byte rgb[] = new byte[3];
|
final byte rgb[] = new byte[3];
|
||||||
size = (biWidth * biHeight) - 1;
|
size = (biWidth * biHeight) - 1;
|
||||||
pad = 4 - ((biWidth * 3) % 4);
|
pad = 4 - ((biWidth * 3) % 4);
|
||||||
if (pad == 4) // <==== Bug correction
|
if (pad == 4)
|
||||||
|
{
|
||||||
pad = 0; // <==== Bug correction
|
pad = 0; // <==== Bug correction
|
||||||
|
}
|
||||||
rowCount = 1;
|
rowCount = 1;
|
||||||
padCount = 0;
|
padCount = 0;
|
||||||
rowIndex = size - biWidth;
|
rowIndex = size - biWidth;
|
||||||
@ -137,14 +139,15 @@ public class BMPFile extends Component {
|
|||||||
rowCount = 1;
|
rowCount = 1;
|
||||||
rowIndex = lastRowIndex - biWidth;
|
rowIndex = lastRowIndex - biWidth;
|
||||||
lastRowIndex = rowIndex;
|
lastRowIndex = rowIndex;
|
||||||
} else
|
} else {
|
||||||
rowCount++;
|
rowCount++;
|
||||||
|
}
|
||||||
rowIndex++;
|
rowIndex++;
|
||||||
}
|
}
|
||||||
// --- Update the size of the file
|
// --- Update the size of the file
|
||||||
bfSize += padCount - pad;
|
bfSize += padCount - pad;
|
||||||
biSizeImage += padCount - pad;
|
biSizeImage += padCount - pad;
|
||||||
} catch (Exception wb) {
|
} catch (final Exception wb) {
|
||||||
wb.printStackTrace();
|
wb.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -160,7 +163,7 @@ public class BMPFile extends Component {
|
|||||||
fo.write(intToWord(bfReserved1));
|
fo.write(intToWord(bfReserved1));
|
||||||
fo.write(intToWord(bfReserved2));
|
fo.write(intToWord(bfReserved2));
|
||||||
fo.write(intToDWord(bfOffBits));
|
fo.write(intToDWord(bfOffBits));
|
||||||
} catch (Exception wbfh) {
|
} catch (final Exception wbfh) {
|
||||||
wbfh.printStackTrace();
|
wbfh.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -184,7 +187,7 @@ public class BMPFile extends Component {
|
|||||||
fo.write(intToDWord(biYPelsPerMeter));
|
fo.write(intToDWord(biYPelsPerMeter));
|
||||||
fo.write(intToDWord(biClrUsed));
|
fo.write(intToDWord(biClrUsed));
|
||||||
fo.write(intToDWord(biClrImportant));
|
fo.write(intToDWord(biClrImportant));
|
||||||
} catch (Exception wbih) {
|
} catch (final Exception wbih) {
|
||||||
wbih.printStackTrace();
|
wbih.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -196,7 +199,7 @@ public class BMPFile extends Component {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
private byte[] intToWord(int parValue) {
|
private byte[] intToWord(int parValue) {
|
||||||
byte retValue[] = new byte[2];
|
final byte retValue[] = new byte[2];
|
||||||
retValue[0] = (byte) (parValue & 0x00FF);
|
retValue[0] = (byte) (parValue & 0x00FF);
|
||||||
retValue[1] = (byte) ((parValue >> 8) & 0x00FF);
|
retValue[1] = (byte) ((parValue >> 8) & 0x00FF);
|
||||||
return (retValue);
|
return (retValue);
|
||||||
@ -209,7 +212,7 @@ public class BMPFile extends Component {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
private byte[] intToDWord(int parValue) {
|
private byte[] intToDWord(int parValue) {
|
||||||
byte retValue[] = new byte[4];
|
final byte retValue[] = new byte[4];
|
||||||
retValue[0] = (byte) (parValue & 0x00FF);
|
retValue[0] = (byte) (parValue & 0x00FF);
|
||||||
retValue[1] = (byte) ((parValue >> 8) & 0x000000FF);
|
retValue[1] = (byte) ((parValue >> 8) & 0x000000FF);
|
||||||
retValue[2] = (byte) ((parValue >> 16) & 0x000000FF);
|
retValue[2] = (byte) ((parValue >> 16) & 0x000000FF);
|
||||||
|
10
src/org/warp/picalculator/KeyboardTest.java
Normal file
10
src/org/warp/picalculator/KeyboardTest.java
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
package org.warp.picalculator;
|
||||||
|
|
||||||
|
import org.warp.picalculator.gui.screens.KeyboardDebugScreen;
|
||||||
|
|
||||||
|
public class KeyboardTest {
|
||||||
|
|
||||||
|
public static void main(String[] args) throws InterruptedException {
|
||||||
|
new Main(new KeyboardDebugScreen());
|
||||||
|
}
|
||||||
|
}
|
@ -1,8 +1,9 @@
|
|||||||
package org.warp.picalculator;
|
package org.warp.picalculator;
|
||||||
|
|
||||||
import org.warp.picalculator.device.Keyboard;
|
import org.warp.picalculator.device.Keyboard;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.screens.LoadingScreen;
|
import org.warp.picalculator.gui.screens.LoadingScreen;
|
||||||
|
import org.warp.picalculator.gui.screens.Screen;
|
||||||
|
|
||||||
import com.pi4j.wiringpi.Gpio;
|
import com.pi4j.wiringpi.Gpio;
|
||||||
|
|
||||||
@ -12,13 +13,19 @@ public class Main {
|
|||||||
public static final boolean zoomed = true;
|
public static final boolean zoomed = true;
|
||||||
public static Main instance;
|
public static Main instance;
|
||||||
public static boolean haxMode = true;
|
public static boolean haxMode = true;
|
||||||
|
public static String[] args;
|
||||||
|
|
||||||
public Main() throws InterruptedException {
|
public Main(String[] args) throws InterruptedException {
|
||||||
|
this(new LoadingScreen(), args);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Main(Screen screen, String[] args) {
|
||||||
instance = this;
|
instance = this;
|
||||||
Thread.currentThread().setPriority(Thread.MAX_PRIORITY);
|
Thread.currentThread().setPriority(Thread.MAX_PRIORITY);
|
||||||
Thread.currentThread().setName("Main thread");
|
Thread.currentThread().setName("Main thread");
|
||||||
|
this.args = args;
|
||||||
beforeStart();
|
beforeStart();
|
||||||
new PIDisplay(new LoadingScreen());
|
new DisplayManager(screen);
|
||||||
Utils.debug.println("Shutdown...");
|
Utils.debug.println("Shutdown...");
|
||||||
beforeShutdown();
|
beforeShutdown();
|
||||||
Utils.debug.println("");
|
Utils.debug.println("");
|
||||||
@ -27,19 +34,15 @@ public class Main {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void beforeStart() {
|
public void beforeStart() {
|
||||||
if (System.getProperty("os.name").equals("Linux")) {
|
if (Utils.isRunningOnRaspberry() && !Utils.isInArray("-noraspi", args)) {
|
||||||
Gpio.wiringPiSetupPhys();
|
Gpio.wiringPiSetupPhys();
|
||||||
Gpio.pinMode(12, Gpio.PWM_OUTPUT);
|
Gpio.pinMode(12, Gpio.PWM_OUTPUT);
|
||||||
} else {
|
} else {
|
||||||
screenPos = new int[]{0,0};
|
screenPos = new int[] { 0, 0 };
|
||||||
Utils.debugOn = true;
|
Utils.debugOn = true;
|
||||||
}
|
}
|
||||||
Utils.debugThirdScreen = Utils.debugOn & false;
|
Utils.debugThirdScreen = Utils.debugOn & false;
|
||||||
PIDisplay.setBrightness(0.5f);
|
DisplayManager.setBrightness(0.5f);
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public void afterStart() {
|
|
||||||
Keyboard.startKeyboard();
|
Keyboard.startKeyboard();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -48,6 +51,6 @@ public class Main {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void main(String[] args) throws InterruptedException {
|
public static void main(String[] args) throws InterruptedException {
|
||||||
new Main();
|
new Main(args);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,56 +1,84 @@
|
|||||||
package org.warp.picalculator;
|
package org.warp.picalculator;
|
||||||
|
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import java.io.IOException;
|
||||||
|
|
||||||
import org.warp.picalculator.gui.graphicengine.Display;
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
import org.warp.picalculator.gui.graphicengine.Drawable;
|
import org.warp.picalculator.gui.graphicengine.Drawable;
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
import org.warp.picalculator.gui.graphicengine.Renderer;
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
import org.warp.picalculator.gui.graphicengine.gpu.GPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.gpu.GPUDisplay;
|
||||||
import org.warp.picalculator.gui.graphicengine.gpu.GPURenderer;
|
import org.warp.picalculator.gui.graphicengine.gpu.GPURenderer;
|
||||||
import org.warp.picalculator.gui.screens.LoadingScreen;
|
import org.warp.picalculator.gui.screens.KeyboardDebugScreen;
|
||||||
|
import org.warp.picalculator.gui.screens.MarioScreen;
|
||||||
|
|
||||||
|
import java.lang.management.ManagementFactory;
|
||||||
|
import java.lang.management.OperatingSystemMXBean;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.lang.reflect.Modifier;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
|
||||||
public class TestGPU {
|
public class TestGPU {
|
||||||
|
|
||||||
public static final GPUDisplay d = new GPUDisplay();
|
public static final GPUDisplay d = new GPUDisplay();
|
||||||
|
|
||||||
public static void main(String[] args) {
|
public static void main(String[] args) throws IOException {
|
||||||
|
new Main(new KeyboardDebugScreen());
|
||||||
|
if (true) return;
|
||||||
Utils.debugOn = true;
|
Utils.debugOn = true;
|
||||||
Utils.debugThirdScreen = false;
|
Utils.debugThirdScreen = false;
|
||||||
d.create();
|
d.create();
|
||||||
|
|
||||||
Scene s = new Scene(d);
|
final Scene s = new Scene(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static class Scene implements Drawable {
|
private static class Scene implements Drawable {
|
||||||
|
|
||||||
private RAWFont[] fonts;
|
private RAWFont exampleFont;
|
||||||
private int[] textures;
|
private final RAWSkin exampleSkin;
|
||||||
|
|
||||||
private GPURenderer r;
|
private final GPURenderer r;
|
||||||
private Display d;
|
private final Display d;
|
||||||
|
|
||||||
public Scene(Display d) {
|
public Scene(Display d) throws IOException {
|
||||||
this.d = d;
|
this.d = d;
|
||||||
this.r = (GPURenderer) d.getRenderer();
|
r = (GPURenderer) d.getRenderer();
|
||||||
|
|
||||||
|
exampleFont = d.loadFont("ex");
|
||||||
|
|
||||||
|
exampleSkin = d.loadSkin("skin.png");
|
||||||
|
|
||||||
d.start(this);
|
d.start(this);
|
||||||
|
|
||||||
// fonts = new RAWFont[1];
|
// fonts = new RAWFont[1];
|
||||||
// textures = new int[100];
|
// textures = new int[100];
|
||||||
// fonts[0] = new RAWFont();
|
// fonts[0] = new RAWFont();
|
||||||
// fonts[0].create("big");
|
// fonts[0].create("big");
|
||||||
new Thread(()->{
|
new Thread(() -> {
|
||||||
try {
|
try {
|
||||||
Thread.sleep(60000);
|
for (int i = 0; i < 12; i++) {
|
||||||
} catch (InterruptedException e) {
|
Utils.printSystemResourcesUsage();
|
||||||
|
Thread.sleep(5000);
|
||||||
|
}
|
||||||
|
} catch (final InterruptedException e) {
|
||||||
// TODO Auto-generated catch block
|
// TODO Auto-generated catch block
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
System.exit(0);
|
System.exit(0);
|
||||||
}).start();
|
}).start();
|
||||||
|
|
||||||
|
d.waitUntilExit();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void refresh() {
|
public void refresh() {
|
||||||
|
exampleSkin.use(d);
|
||||||
|
r.glClearColor(0xFFD0FDCF);
|
||||||
|
r.glClear(d.getWidth(), d.getHeight());
|
||||||
|
r.glColor3f(1.0f, 1.0f, 1.0f);
|
||||||
|
r.glFillRect(2, 2, 160, 160, 0, 0, 16, 16);
|
||||||
|
exampleFont.use(d);
|
||||||
|
r.glColor3f(1, 0, 0);
|
||||||
|
r.glDrawStringLeft(10, 170, "Prova! 123456789");
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -1,9 +1,17 @@
|
|||||||
package org.warp.picalculator;
|
package org.warp.picalculator;
|
||||||
|
|
||||||
|
import java.io.BufferedReader;
|
||||||
import java.io.ByteArrayOutputStream;
|
import java.io.ByteArrayOutputStream;
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.FileInputStream;
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.io.InputStream;
|
import java.io.InputStream;
|
||||||
|
import java.io.InputStreamReader;
|
||||||
import java.io.StringWriter;
|
import java.io.StringWriter;
|
||||||
|
import java.lang.management.ManagementFactory;
|
||||||
|
import java.lang.management.OperatingSystemMXBean;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.lang.reflect.Modifier;
|
||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
import java.math.BigInteger;
|
import java.math.BigInteger;
|
||||||
import java.math.RoundingMode;
|
import java.math.RoundingMode;
|
||||||
@ -12,7 +20,7 @@ import java.util.List;
|
|||||||
|
|
||||||
import org.nevec.rjm.BigDecimalMath;
|
import org.nevec.rjm.BigDecimalMath;
|
||||||
import org.nevec.rjm.Rational;
|
import org.nevec.rjm.Rational;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
import org.warp.picalculator.math.functions.AnteriorFunction;
|
import org.warp.picalculator.math.functions.AnteriorFunction;
|
||||||
import org.warp.picalculator.math.functions.Division;
|
import org.warp.picalculator.math.functions.Division;
|
||||||
@ -61,7 +69,7 @@ public class Utils {
|
|||||||
|
|
||||||
public static boolean isInArray(String ch, String[] a) {
|
public static boolean isInArray(String ch, String[] a) {
|
||||||
boolean contains = false;
|
boolean contains = false;
|
||||||
for (String c : a) {
|
for (final String c : a) {
|
||||||
if (c.equals(ch)) {
|
if (c.equals(ch)) {
|
||||||
contains = true;
|
contains = true;
|
||||||
break;
|
break;
|
||||||
@ -70,13 +78,13 @@ public class Utils {
|
|||||||
return contains;
|
return contains;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static final String[] regexNormalSymbols = new String[]{"\\", ".", "[", "]", "{", "}", "(", ")", "*", "+", "-", "?", "^", "$", "|"};
|
private static final String[] regexNormalSymbols = new String[] { "\\", ".", "[", "]", "{", "}", "(", ")", "*", "+", "-", "?", "^", "$", "|" };
|
||||||
|
|
||||||
public static String ArrayToRegex(String[] array) {
|
public static String ArrayToRegex(String[] array) {
|
||||||
String regex = null;
|
String regex = null;
|
||||||
for (String symbol : array) {
|
for (final String symbol : array) {
|
||||||
boolean contained = false;
|
boolean contained = false;
|
||||||
for (String smb : regexNormalSymbols) {
|
for (final String smb : regexNormalSymbols) {
|
||||||
if (smb.equals(symbol)) {
|
if (smb.equals(symbol)) {
|
||||||
contained = true;
|
contained = true;
|
||||||
break;
|
break;
|
||||||
@ -100,17 +108,17 @@ public class Utils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static String[] concat(String[] a, String[] b) {
|
public static String[] concat(String[] a, String[] b) {
|
||||||
int aLen = a.length;
|
final int aLen = a.length;
|
||||||
int bLen = b.length;
|
final int bLen = b.length;
|
||||||
String[] c = new String[aLen + bLen];
|
final String[] c = new String[aLen + bLen];
|
||||||
System.arraycopy(a, 0, c, 0, aLen);
|
System.arraycopy(a, 0, c, 0, aLen);
|
||||||
System.arraycopy(b, 0, c, aLen, bLen);
|
System.arraycopy(b, 0, c, aLen, bLen);
|
||||||
return c;
|
return c;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String[] add(String[] a, String b) {
|
public static String[] add(String[] a, String b) {
|
||||||
int aLen = a.length;
|
final int aLen = a.length;
|
||||||
String[] c = new String[aLen + 1];
|
final String[] c = new String[aLen + 1];
|
||||||
System.arraycopy(a, 0, c, 0, aLen);
|
System.arraycopy(a, 0, c, 0, aLen);
|
||||||
c[aLen] = b;
|
c[aLen] = b;
|
||||||
return c;
|
return c;
|
||||||
@ -249,7 +257,7 @@ public class Utils {
|
|||||||
|
|
||||||
public static boolean areThereOtherSettedUpFunctions(ArrayList<Function> fl) {
|
public static boolean areThereOtherSettedUpFunctions(ArrayList<Function> fl) {
|
||||||
for (int i = 0; i < fl.size(); i++) {
|
for (int i = 0; i < fl.size(); i++) {
|
||||||
if (!(fl.get(i) instanceof Number || fl.get(i) instanceof Variable || fl.get(i) instanceof Sum || fl.get(i) instanceof SumSubtraction || fl.get(i) instanceof Expression || fl.get(i) instanceof AnteriorFunction || fl.get(i) instanceof Multiplication || fl.get(i) instanceof Division)) {
|
if (!(fl.get(i) instanceof Number || fl.get(i) instanceof Variable || fl.get(i) instanceof Sum || fl.get(i) instanceof SumSubtraction || fl.get(i) instanceof Expression || fl.get(i) instanceof AnteriorFunction || fl.get(i) instanceof Multiplication || fl.get(i) instanceof Division)) {
|
||||||
if (fl.get(i) instanceof AnteriorFunction) {
|
if (fl.get(i) instanceof AnteriorFunction) {
|
||||||
if (((AnteriorFunction) fl.get(i)).getVariable() == null) {
|
if (((AnteriorFunction) fl.get(i)).getVariable() == null) {
|
||||||
return true;
|
return true;
|
||||||
@ -269,7 +277,7 @@ public class Utils {
|
|||||||
public static Rational getRational(BigDecimal str) {
|
public static Rational getRational(BigDecimal str) {
|
||||||
try {
|
try {
|
||||||
return getRational(str.toString());
|
return getRational(str.toString());
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
//E' IMPOSSIBILE CHE VENGA THROWATO UN ERRORE
|
//E' IMPOSSIBILE CHE VENGA THROWATO UN ERRORE
|
||||||
return new Rational("0");
|
return new Rational("0");
|
||||||
}
|
}
|
||||||
@ -278,17 +286,17 @@ public class Utils {
|
|||||||
public static Rational getRational(String str) throws Error {
|
public static Rational getRational(String str) throws Error {
|
||||||
try {
|
try {
|
||||||
return new Rational(str);
|
return new Rational(str);
|
||||||
} catch (NumberFormatException ex) {
|
} catch (final NumberFormatException ex) {
|
||||||
if (new BigDecimal(str).compareTo(new BigDecimal(8000.0)) < 0 && new BigDecimal(str).compareTo(new BigDecimal(-8000.0)) > 0) {
|
if (new BigDecimal(str).compareTo(new BigDecimal(8000.0)) < 0 && new BigDecimal(str).compareTo(new BigDecimal(-8000.0)) > 0) {
|
||||||
if (str.equals("-")) {
|
if (str.equals("-")) {
|
||||||
str = "-1";
|
str = "-1";
|
||||||
}
|
}
|
||||||
long bits = Double.doubleToLongBits(Double.parseDouble(str));
|
final long bits = Double.doubleToLongBits(Double.parseDouble(str));
|
||||||
|
|
||||||
long sign = bits >>> 63;
|
final long sign = bits >>> 63;
|
||||||
long exponent = ((bits >>> 52) ^ (sign << 11)) - 1023;
|
final long exponent = ((bits >>> 52) ^ (sign << 11)) - 1023;
|
||||||
long fraction = bits << 12; // bits are "reversed" but that's
|
final long fraction = bits << 12; // bits are "reversed" but that's
|
||||||
// not a problem
|
// not a problem
|
||||||
|
|
||||||
long a = 1L;
|
long a = 1L;
|
||||||
long b = 1L;
|
long b = 1L;
|
||||||
@ -298,13 +306,15 @@ public class Utils {
|
|||||||
b *= 2;
|
b *= 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (exponent > 0)
|
if (exponent > 0) {
|
||||||
a *= 1 << exponent;
|
a *= 1 << exponent;
|
||||||
else
|
} else {
|
||||||
b *= 1 << -exponent;
|
b *= 1 << -exponent;
|
||||||
|
}
|
||||||
|
|
||||||
if (sign == 1)
|
if (sign == 1) {
|
||||||
a *= -1;
|
a *= -1;
|
||||||
|
}
|
||||||
|
|
||||||
if (b == 0) {
|
if (b == 0) {
|
||||||
a = 0;
|
a = 0;
|
||||||
@ -313,11 +323,11 @@ public class Utils {
|
|||||||
|
|
||||||
return new Rational(new BigInteger(a + ""), new BigInteger(b + ""));
|
return new Rational(new BigInteger(a + ""), new BigInteger(b + ""));
|
||||||
} else {
|
} else {
|
||||||
BigDecimal original = new BigDecimal(str);
|
final BigDecimal original = new BigDecimal(str);
|
||||||
|
|
||||||
BigInteger numerator = original.unscaledValue();
|
final BigInteger numerator = original.unscaledValue();
|
||||||
|
|
||||||
BigInteger denominator = BigDecimalMath.pow(BigDecimal.TEN, new BigDecimal(original.scale())).toBigIntegerExact();
|
final BigInteger denominator = BigDecimalMath.pow(BigDecimal.TEN, new BigDecimal(original.scale())).toBigIntegerExact();
|
||||||
|
|
||||||
return new Rational(numerator, denominator);
|
return new Rational(numerator, denominator);
|
||||||
}
|
}
|
||||||
@ -332,7 +342,7 @@ public class Utils {
|
|||||||
if (variables.size() != variables2.size()) {
|
if (variables.size() != variables2.size()) {
|
||||||
return false;
|
return false;
|
||||||
} else {
|
} else {
|
||||||
for (Variable v : variables) {
|
for (final Variable v : variables) {
|
||||||
if (!variables2.contains(v)) {
|
if (!variables2.contains(v)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -343,17 +353,17 @@ public class Utils {
|
|||||||
|
|
||||||
public static void writeSquareRoot(Function var, int x, int y, boolean small) {
|
public static void writeSquareRoot(Function var, int x, int y, boolean small) {
|
||||||
var.setSmall(small);
|
var.setSmall(small);
|
||||||
int w1 = var.getWidth();
|
final int w1 = var.getWidth();
|
||||||
int h1 = var.getHeight();
|
final int h1 = var.getHeight();
|
||||||
int wsegno = 5;
|
final int wsegno = 5;
|
||||||
int hsegno = h1 + 2;
|
final int hsegno = h1 + 2;
|
||||||
|
|
||||||
var.draw(x + wsegno, y + (hsegno - h1));
|
var.draw(x + wsegno, y + (hsegno - h1));
|
||||||
|
|
||||||
PIDisplay.renderer.glDrawLine(x + 1, y + hsegno - 3, x + 3, y + hsegno - 1);
|
DisplayManager.renderer.glDrawLine(x + 1, y + hsegno - 3, x + 3, y + hsegno - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 3, y + (hsegno - 1) / 2 + 1, x + 3, y + hsegno - 1);
|
DisplayManager.renderer.glDrawLine(x + 3, y + (hsegno - 1) / 2 + 1, x + 3, y + hsegno - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 4, y, x + 4, y + (hsegno - 1) / 2);
|
DisplayManager.renderer.glDrawLine(x + 4, y, x + 4, y + (hsegno - 1) / 2);
|
||||||
PIDisplay.renderer.glDrawLine(x + 4, y, x + 4 + 1 + w1 + 1, y);
|
DisplayManager.renderer.glDrawLine(x + 4, y, x + 4 + 1 + w1 + 1, y);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static final int getFontHeight() {
|
public static final int getFontHeight() {
|
||||||
@ -365,7 +375,7 @@ public class Utils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static final RAWFont getFont(boolean small, boolean zoomed) {
|
public static final RAWFont getFont(boolean small, boolean zoomed) {
|
||||||
return PIDisplay.fonts[getFontIndex(small, zoomed)];
|
return DisplayManager.fonts[getFontIndex(small, zoomed)];
|
||||||
}
|
}
|
||||||
|
|
||||||
public static final int getFontIndex(boolean small, boolean zoomed) {
|
public static final int getFontIndex(boolean small, boolean zoomed) {
|
||||||
@ -391,44 +401,44 @@ public class Utils {
|
|||||||
public static final int getFontHeight(boolean small, boolean zoomed) {
|
public static final int getFontHeight(boolean small, boolean zoomed) {
|
||||||
if (small) {
|
if (small) {
|
||||||
if (zoomed) {
|
if (zoomed) {
|
||||||
return PIDisplay.glyphsHeight[3];
|
return DisplayManager.glyphsHeight[3];
|
||||||
} else {
|
} else {
|
||||||
return PIDisplay.glyphsHeight[1];
|
return DisplayManager.glyphsHeight[1];
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (zoomed) {
|
if (zoomed) {
|
||||||
return PIDisplay.glyphsHeight[2];
|
return DisplayManager.glyphsHeight[2];
|
||||||
} else {
|
} else {
|
||||||
return PIDisplay.glyphsHeight[0];
|
return DisplayManager.glyphsHeight[0];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static byte[] convertStreamToByteArray(InputStream stream, long size) throws IOException {
|
public static byte[] convertStreamToByteArray(InputStream stream, long size) throws IOException {
|
||||||
|
|
||||||
// check to ensure that file size is not larger than Integer.MAX_VALUE.
|
// check to ensure that file size is not larger than Integer.MAX_VALUE.
|
||||||
if (size > Integer.MAX_VALUE) {
|
if (size > Integer.MAX_VALUE) {
|
||||||
return new byte[0];
|
return new byte[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
byte[] buffer = new byte[(int)size];
|
final byte[] buffer = new byte[(int) size];
|
||||||
ByteArrayOutputStream os = new ByteArrayOutputStream();
|
final ByteArrayOutputStream os = new ByteArrayOutputStream();
|
||||||
|
|
||||||
int line = 0;
|
int line = 0;
|
||||||
// read bytes from stream, and store them in buffer
|
// read bytes from stream, and store them in buffer
|
||||||
while ((line = stream.read(buffer)) != -1) {
|
while ((line = stream.read(buffer)) != -1) {
|
||||||
// Writes bytes from byte array (buffer) into output stream.
|
// Writes bytes from byte array (buffer) into output stream.
|
||||||
os.write(buffer, 0, line);
|
os.write(buffer, 0, line);
|
||||||
}
|
}
|
||||||
stream.close();
|
stream.close();
|
||||||
os.flush();
|
os.flush();
|
||||||
os.close();
|
os.close();
|
||||||
return os.toByteArray();
|
return os.toByteArray();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static int[] realBytes(byte[] bytes) {
|
public static int[] realBytes(byte[] bytes) {
|
||||||
int len = bytes.length;
|
final int len = bytes.length;
|
||||||
int[] realbytes = new int[len];
|
final int[] realbytes = new int[len];
|
||||||
for (int i = 0; i < len; i++) {
|
for (int i = 0; i < len; i++) {
|
||||||
realbytes[i] = Byte.toUnsignedInt(bytes[i]);
|
realbytes[i] = Byte.toUnsignedInt(bytes[i]);
|
||||||
}
|
}
|
||||||
@ -436,7 +446,7 @@ public class Utils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static boolean allSolved(List<Function> expressions) throws Error {
|
public static boolean allSolved(List<Function> expressions) throws Error {
|
||||||
for (Function itm : expressions) {
|
for (final Function itm : expressions) {
|
||||||
if (itm.isSolved() == false) {
|
if (itm.isSolved() == false) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -445,22 +455,26 @@ public class Utils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static Function[][] joinFunctionsResults(List<Function> l1, List<Function> l2) {
|
public static Function[][] joinFunctionsResults(List<Function> l1, List<Function> l2) {
|
||||||
int size1 = l1.size();
|
final int size1 = l1.size();
|
||||||
int size2 = l2.size();
|
final int size2 = l2.size();
|
||||||
int cur1 = 0;
|
int cur1 = 0;
|
||||||
int cur2 = 0;
|
int cur2 = 0;
|
||||||
int total = l1.size()*l2.size();
|
final int total = l1.size() * l2.size();
|
||||||
Function[][] results = new Function[total][2];
|
final Function[][] results = new Function[total][2];
|
||||||
for (int i = 0; i < total; i++) {
|
for (int i = 0; i < total; i++) {
|
||||||
results[i] = new Function[]{l1.get(cur1), l2.get(cur2)};
|
results[i] = new Function[] { l1.get(cur1), l2.get(cur2) };
|
||||||
if (i % size2 == 0) {
|
if (i % size2 == 0) {
|
||||||
cur1+=1;
|
cur1 += 1;
|
||||||
}
|
}
|
||||||
if (i % size1 == 0) {
|
if (i % size1 == 0) {
|
||||||
cur2+=1;
|
cur2 += 1;
|
||||||
|
}
|
||||||
|
if (cur1 >= size1) {
|
||||||
|
cur1 = 0;
|
||||||
|
}
|
||||||
|
if (cur2 >= size2) {
|
||||||
|
cur2 = 0;
|
||||||
}
|
}
|
||||||
if (cur1 >= size1) cur1 = 0;
|
|
||||||
if (cur2 >= size2) cur2 = 0;
|
|
||||||
}
|
}
|
||||||
return results;
|
return results;
|
||||||
}
|
}
|
||||||
@ -477,28 +491,97 @@ public class Utils {
|
|||||||
public static CharSequence multipleChars(String string, int i) {
|
public static CharSequence multipleChars(String string, int i) {
|
||||||
String result = "";
|
String result = "";
|
||||||
for (int j = 0; j < i; j++) {
|
for (int j = 0; j < i; j++) {
|
||||||
result+=string;
|
result += string;
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static boolean isIntegerValue(BigDecimal bd) {
|
public static boolean isIntegerValue(BigDecimal bd) {
|
||||||
return bd.signum() == 0 || bd.scale() <= 0 || bd.stripTrailingZeros().scale() <= 0;
|
return bd.signum() == 0 || bd.scale() <= 0 || bd.stripTrailingZeros().scale() <= 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static <T> String arrayToString(T... data) {
|
public static <T> String arrayToString(T... data) {
|
||||||
String sdata = "";
|
String sdata = "";
|
||||||
for (T o : data) {
|
for (final T o : data) {
|
||||||
sdata += ","+o.toString();
|
sdata += "," + o.toString();
|
||||||
}
|
}
|
||||||
return sdata.substring(1);
|
return sdata.substring(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String arrayToString(boolean... data) {
|
public static String arrayToString(boolean... data) {
|
||||||
String sdata = "";
|
String sdata = "";
|
||||||
for (boolean o : data) {
|
for (final boolean o : data) {
|
||||||
sdata += (o)?1:0;
|
sdata += (o) ? 1 : 0;
|
||||||
}
|
}
|
||||||
return sdata;
|
return sdata;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static void printSystemResourcesUsage() {
|
||||||
|
System.out.println("============");
|
||||||
|
OperatingSystemMXBean operatingSystemMXBean = ManagementFactory.getOperatingSystemMXBean();
|
||||||
|
for (Method method : operatingSystemMXBean.getClass().getDeclaredMethods()) {
|
||||||
|
method.setAccessible(true);
|
||||||
|
if (method.getName().startsWith("get") && Modifier.isPublic(method.getModifiers())) {
|
||||||
|
Object value;
|
||||||
|
try {
|
||||||
|
value = method.invoke(operatingSystemMXBean);
|
||||||
|
} catch (Exception e) {
|
||||||
|
value = e;
|
||||||
|
} // try
|
||||||
|
boolean percent = false;
|
||||||
|
boolean mb = false;
|
||||||
|
String displayName = method.getName();
|
||||||
|
String displayValue = value.toString();
|
||||||
|
if (displayName.endsWith("CpuLoad")) {
|
||||||
|
percent = true;
|
||||||
|
}
|
||||||
|
if (displayName.endsWith("MemorySize")) {
|
||||||
|
mb = true;
|
||||||
|
}
|
||||||
|
ArrayList<String> arr = new ArrayList<>();
|
||||||
|
arr.add("getFreePhysicalMemorySize");
|
||||||
|
arr.add("getProcessCpuLoad");
|
||||||
|
arr.add("getSystemCpuLoad");
|
||||||
|
arr.add("getTotalPhysicalMemorySize");
|
||||||
|
if (arr.contains(displayName)) {
|
||||||
|
if (percent) {
|
||||||
|
try {
|
||||||
|
System.out.println(displayName + " = " + (((int)(Float.parseFloat(displayValue) * 10000f))/100f) + "%");
|
||||||
|
}catch(Exception ex) {
|
||||||
|
System.out.println(displayName + " = " + displayValue);
|
||||||
|
}
|
||||||
|
} else if (mb) {
|
||||||
|
try {
|
||||||
|
System.out.println(displayName + " = " + (Long.parseLong(displayValue) / 1024L / 1024L) + " MB");
|
||||||
|
}catch(Exception ex) {
|
||||||
|
System.out.println(displayName + " = " + displayValue);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
System.out.println(displayName + " = " + displayValue);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} // if
|
||||||
|
} // for
|
||||||
|
System.out.println("============");
|
||||||
|
}
|
||||||
|
|
||||||
|
public static boolean isRunningOnRaspberry() {
|
||||||
|
if (System.getProperty("os.name").equals("Linux")) {
|
||||||
|
final File file = new File("/etc", "os-release");
|
||||||
|
try (FileInputStream fis = new FileInputStream(file);
|
||||||
|
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(fis))) {
|
||||||
|
String string;
|
||||||
|
while ((string = bufferedReader.readLine()) != null) {
|
||||||
|
if (string.toLowerCase().contains("raspbian")) {
|
||||||
|
if (string.toLowerCase().contains("name")) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (final Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -5,8 +5,7 @@ import java.awt.event.KeyEvent;
|
|||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.device.chip.ParallelToSerial;
|
import org.warp.picalculator.device.chip.ParallelToSerial;
|
||||||
import org.warp.picalculator.device.chip.SerialToParallel;
|
import org.warp.picalculator.device.chip.SerialToParallel;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
|
||||||
import org.warp.picalculator.gui.screens.KeyboardDebugScreen;
|
import org.warp.picalculator.gui.screens.KeyboardDebugScreen;
|
||||||
import org.warp.picalculator.gui.screens.MarioScreen;
|
import org.warp.picalculator.gui.screens.MarioScreen;
|
||||||
import org.warp.picalculator.gui.screens.Screen;
|
import org.warp.picalculator.gui.screens.Screen;
|
||||||
@ -29,21 +28,20 @@ public class Keyboard {
|
|||||||
|
|
||||||
private static volatile boolean[][] precedentStates = new boolean[8][8];
|
private static volatile boolean[][] precedentStates = new boolean[8][8];
|
||||||
public static volatile boolean[][] debugKeysDown = new boolean[8][8];
|
public static volatile boolean[][] debugKeysDown = new boolean[8][8];
|
||||||
public static volatile KeyEvent debugKeyEvent;
|
public static volatile int debugKeyCode = -1;
|
||||||
|
|
||||||
public static void startKeyboard() {
|
public static void startKeyboard() {
|
||||||
Thread kt = new Thread(()->{
|
final Thread kt = new Thread(() -> {
|
||||||
if (Utils.debugOn) {
|
if (Utils.debugOn) {
|
||||||
try {
|
try {
|
||||||
while(true) {
|
while (true) {
|
||||||
if (debugKeyEvent != null) {
|
if (debugKeyCode != -1) {
|
||||||
debugKeyPressed(debugKeyEvent);
|
debugKeyPressed(debugKeyCode);
|
||||||
debugKeyEvent = null;
|
debugKeyCode = -1;
|
||||||
}
|
}
|
||||||
Thread.sleep(50);
|
Thread.sleep(50);
|
||||||
}
|
}
|
||||||
} catch (InterruptedException e) {
|
} catch (final InterruptedException e) {}
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
Gpio.pinMode(CLK_INH_pin, Gpio.OUTPUT);
|
Gpio.pinMode(CLK_INH_pin, Gpio.OUTPUT);
|
||||||
Gpio.pinMode(RCK_pin, Gpio.OUTPUT);
|
Gpio.pinMode(RCK_pin, Gpio.OUTPUT);
|
||||||
@ -58,12 +56,12 @@ public class Keyboard {
|
|||||||
Gpio.digitalWrite(SH_LD_pin, false);
|
Gpio.digitalWrite(SH_LD_pin, false);
|
||||||
Gpio.digitalWrite(SCK_and_CLK_pin, false);
|
Gpio.digitalWrite(SCK_and_CLK_pin, false);
|
||||||
Gpio.digitalWrite(QH_pin, false);
|
Gpio.digitalWrite(QH_pin, false);
|
||||||
SerialToParallel chip1 = new SerialToParallel(RCK_pin, SCK_and_CLK_pin /*SCK*/, SER_pin);
|
final SerialToParallel chip1 = new SerialToParallel(RCK_pin, SCK_and_CLK_pin /*SCK*/, SER_pin);
|
||||||
ParallelToSerial chip2 = new ParallelToSerial(SH_LD_pin, CLK_INH_pin, QH_pin, SCK_and_CLK_pin/*CLK*/);
|
final ParallelToSerial chip2 = new ParallelToSerial(SH_LD_pin, CLK_INH_pin, QH_pin, SCK_and_CLK_pin/*CLK*/);
|
||||||
|
|
||||||
KeyboardDebugScreen.log("Started keyboard system");
|
KeyboardDebugScreen.log("Started keyboard system");
|
||||||
|
|
||||||
while(true) {
|
while (true) {
|
||||||
boolean[] data;
|
boolean[] data;
|
||||||
for (int col = 0; col < 8; col++) {
|
for (int col = 0; col < 8; col++) {
|
||||||
data = new boolean[8];
|
data = new boolean[8];
|
||||||
@ -75,12 +73,12 @@ public class Keyboard {
|
|||||||
|
|
||||||
for (int row = 0; row < 8; row++) {
|
for (int row = 0; row < 8; row++) {
|
||||||
if (data[row] == true && precedentStates[row][col] == false) {
|
if (data[row] == true && precedentStates[row][col] == false) {
|
||||||
System.out.println("Pressed button at "+(row+1) +", "+(col+1));
|
System.out.println("Pressed button at " + (row + 1) + ", " + (col + 1));
|
||||||
KeyboardDebugScreen.log("Pressed button at "+(row+1) +", "+(col+1));
|
KeyboardDebugScreen.log("Pressed button at " + (row + 1) + ", " + (col + 1));
|
||||||
keyPressedRaw(row+1, col+1);
|
keyPressedRaw(row + 1, col + 1);
|
||||||
} else if (data[row] == false && precedentStates[row][col] == true) {
|
} else if (data[row] == false && precedentStates[row][col] == true) {
|
||||||
keyReleasedRaw(row+1, col+1);
|
keyReleasedRaw(row + 1, col + 1);
|
||||||
KeyboardDebugScreen.log("Released button at "+(row+1) +", "+(col+1));
|
KeyboardDebugScreen.log("Released button at " + (row + 1) + ", " + (col + 1));
|
||||||
}
|
}
|
||||||
precedentStates[row][col] = data[row];
|
precedentStates[row][col] = data[row];
|
||||||
}
|
}
|
||||||
@ -94,8 +92,8 @@ public class Keyboard {
|
|||||||
kt.start();
|
kt.start();
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void debugKeyPressed(KeyEvent arg0) {
|
private static void debugKeyPressed(int keyCode) {
|
||||||
switch (arg0.getKeyCode()) {
|
switch (keyCode) {
|
||||||
case KeyEvent.VK_ESCAPE:
|
case KeyEvent.VK_ESCAPE:
|
||||||
Keyboard.keyPressed(Key.POWER);
|
Keyboard.keyPressed(Key.POWER);
|
||||||
break;
|
break;
|
||||||
@ -177,6 +175,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_ENTER:
|
||||||
case KeyEvent.VK_ENTER:
|
case KeyEvent.VK_ENTER:
|
||||||
if (Keyboard.shift) {
|
if (Keyboard.shift) {
|
||||||
Keyboard.keyPressed(Key.SIMPLIFY);
|
Keyboard.keyPressed(Key.SIMPLIFY);
|
||||||
@ -187,7 +186,7 @@ public class Keyboard {
|
|||||||
}
|
}
|
||||||
int row = 2;
|
int row = 2;
|
||||||
int col = 1;
|
int col = 1;
|
||||||
Keyboard.debugKeysDown[row-1][col-1] = true;
|
Keyboard.debugKeysDown[row - 1][col - 1] = true;
|
||||||
break;
|
break;
|
||||||
case KeyEvent.VK_1:
|
case KeyEvent.VK_1:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
@ -265,6 +264,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_ADD:
|
||||||
case KeyEvent.VK_ADD:
|
case KeyEvent.VK_ADD:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.PLUS);
|
Keyboard.keyPressed(Key.PLUS);
|
||||||
@ -274,6 +274,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_SUBTRACT:
|
||||||
case KeyEvent.VK_SUBTRACT:
|
case KeyEvent.VK_SUBTRACT:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.MINUS);
|
Keyboard.keyPressed(Key.MINUS);
|
||||||
@ -281,6 +282,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_MULTIPLY:
|
||||||
case KeyEvent.VK_MULTIPLY:
|
case KeyEvent.VK_MULTIPLY:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.MULTIPLY);
|
Keyboard.keyPressed(Key.MULTIPLY);
|
||||||
@ -288,6 +290,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_DIVIDE:
|
||||||
case KeyEvent.VK_DIVIDE:
|
case KeyEvent.VK_DIVIDE:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.DIVIDE);
|
Keyboard.keyPressed(Key.DIVIDE);
|
||||||
@ -302,6 +305,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_DELETE:
|
||||||
case KeyEvent.VK_DELETE:
|
case KeyEvent.VK_DELETE:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.RESET);
|
Keyboard.keyPressed(Key.RESET);
|
||||||
@ -309,28 +313,31 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_LEFT:
|
||||||
case KeyEvent.VK_LEFT:
|
case KeyEvent.VK_LEFT:
|
||||||
//LEFT
|
//LEFT
|
||||||
row = 2;
|
row = 2;
|
||||||
col = 3;
|
col = 3;
|
||||||
Keyboard.debugKeysDown[row-1][col-1] = true;
|
Keyboard.debugKeysDown[row - 1][col - 1] = true;
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.LEFT);
|
Keyboard.keyPressed(Key.LEFT);
|
||||||
} else {
|
} else {
|
||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_RIGHT:
|
||||||
case KeyEvent.VK_RIGHT:
|
case KeyEvent.VK_RIGHT:
|
||||||
//RIGHT
|
//RIGHT
|
||||||
row = 2;
|
row = 2;
|
||||||
col = 5;
|
col = 5;
|
||||||
Keyboard.debugKeysDown[row-1][col-1] = true;
|
Keyboard.debugKeysDown[row - 1][col - 1] = true;
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.RIGHT);
|
Keyboard.keyPressed(Key.RIGHT);
|
||||||
} else {
|
} else {
|
||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_NUMPAD4:
|
||||||
case KeyEvent.VK_NUMPAD4:
|
case KeyEvent.VK_NUMPAD4:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.HISTORY_BACK);
|
Keyboard.keyPressed(Key.HISTORY_BACK);
|
||||||
@ -338,6 +345,7 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_NUMPAD6:
|
||||||
case KeyEvent.VK_NUMPAD6:
|
case KeyEvent.VK_NUMPAD6:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
Keyboard.keyPressed(Key.HISTORY_FORWARD);
|
Keyboard.keyPressed(Key.HISTORY_FORWARD);
|
||||||
@ -352,21 +360,26 @@ public class Keyboard {
|
|||||||
Keyboard.keyPressed(Key.NONE);
|
Keyboard.keyPressed(Key.NONE);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_SHIFT:
|
||||||
case KeyEvent.VK_SHIFT:
|
case KeyEvent.VK_SHIFT:
|
||||||
Keyboard.keyPressed(Key.SHIFT);
|
Keyboard.keyPressed(Key.SHIFT);
|
||||||
break;
|
break;
|
||||||
case KeyEvent.VK_A:
|
case KeyEvent.VK_A:
|
||||||
Keyboard.keyPressed(Key.ALPHA);
|
Keyboard.keyPressed(Key.ALPHA);
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_NUMPAD1:
|
||||||
case KeyEvent.VK_NUMPAD1:
|
case KeyEvent.VK_NUMPAD1:
|
||||||
Keyboard.keyPressed(Key.SQRT);
|
Keyboard.keyPressed(Key.SQRT);
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_NUMPAD2:
|
||||||
case KeyEvent.VK_NUMPAD2:
|
case KeyEvent.VK_NUMPAD2:
|
||||||
Keyboard.keyPressed(Key.ROOT);
|
Keyboard.keyPressed(Key.ROOT);
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_NUMPAD3:
|
||||||
case KeyEvent.VK_NUMPAD3:
|
case KeyEvent.VK_NUMPAD3:
|
||||||
Keyboard.keyPressed(Key.POWER_OF_2);
|
Keyboard.keyPressed(Key.POWER_OF_2);
|
||||||
break;
|
break;
|
||||||
|
case com.jogamp.newt.event.KeyEvent.VK_NUMPAD5:
|
||||||
case KeyEvent.VK_NUMPAD5:
|
case KeyEvent.VK_NUMPAD5:
|
||||||
Keyboard.keyPressed(Key.POWER_OF_x);
|
Keyboard.keyPressed(Key.POWER_OF_x);
|
||||||
break;
|
break;
|
||||||
@ -375,9 +388,9 @@ public class Keyboard {
|
|||||||
|
|
||||||
public static boolean isKeyDown(int row, int col) {
|
public static boolean isKeyDown(int row, int col) {
|
||||||
if (Utils.debugOn == false) {
|
if (Utils.debugOn == false) {
|
||||||
return precedentStates[row-1][col-1];
|
return precedentStates[row - 1][col - 1];
|
||||||
} else {
|
} else {
|
||||||
return debugKeysDown[row-1][col-1];
|
return debugKeysDown[row - 1][col - 1];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -395,7 +408,7 @@ public class Keyboard {
|
|||||||
if (row == 1 && col == 1) {
|
if (row == 1 && col == 1) {
|
||||||
keyPressed(Key.SHIFT);
|
keyPressed(Key.SHIFT);
|
||||||
} else if (row == 1 && col == 2) {
|
} else if (row == 1 && col == 2) {
|
||||||
keyPressed(Key.ALPHA);
|
keyPressed(Key.ALPHA);
|
||||||
} else if (row == 1 && col == 7) {
|
} else if (row == 1 && col == 7) {
|
||||||
if (shift) {
|
if (shift) {
|
||||||
keyPressed(Key.BRIGHTNESS_CYCLE_REVERSE);
|
keyPressed(Key.BRIGHTNESS_CYCLE_REVERSE);
|
||||||
@ -580,7 +593,7 @@ public class Keyboard {
|
|||||||
} else {
|
} else {
|
||||||
keyPressed(Key.LEFT);
|
keyPressed(Key.LEFT);
|
||||||
}
|
}
|
||||||
} else if (row ==2 && col == 5) {
|
} else if (row == 2 && col == 5) {
|
||||||
if (shift) {
|
if (shift) {
|
||||||
keyPressed(Key.NONE);
|
keyPressed(Key.NONE);
|
||||||
} else if (alpha) {
|
} else if (alpha) {
|
||||||
@ -664,8 +677,7 @@ public class Keyboard {
|
|||||||
System.out.println("PREMUTO >");
|
System.out.println("PREMUTO >");
|
||||||
keyPressed(Key.HISTORY_FORWARD);
|
keyPressed(Key.HISTORY_FORWARD);
|
||||||
}
|
}
|
||||||
} else {
|
} else {}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void stopKeyboard() {
|
public static void stopKeyboard() {
|
||||||
@ -680,15 +692,15 @@ public class Keyboard {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static void keyPressed(Key k) {
|
public static void keyPressed(Key k) {
|
||||||
if (PIDisplay.INSTANCE != null) {
|
if (DisplayManager.INSTANCE != null) {
|
||||||
Screen scr = PIDisplay.INSTANCE.getScreen();
|
final Screen scr = DisplayManager.INSTANCE.getScreen();
|
||||||
boolean refresh = false;
|
boolean refresh = false;
|
||||||
if(scr != null && scr.initialized && scr.keyPressed(k)) {
|
if (scr != null && scr.initialized && scr.keyPressed(k)) {
|
||||||
refresh = true;
|
refresh = true;
|
||||||
} else {
|
} else {
|
||||||
switch (k) {
|
switch (k) {
|
||||||
case POWER:
|
case POWER:
|
||||||
PIDisplay.display.destroy();
|
DisplayManager.display.destroy();
|
||||||
break;
|
break;
|
||||||
case NONE:
|
case NONE:
|
||||||
break;
|
break;
|
||||||
@ -696,20 +708,20 @@ public class Keyboard {
|
|||||||
letterPressed('X');
|
letterPressed('X');
|
||||||
break;
|
break;
|
||||||
case BRIGHTNESS_CYCLE:
|
case BRIGHTNESS_CYCLE:
|
||||||
PIDisplay.cycleBrightness(false);
|
DisplayManager.cycleBrightness(false);
|
||||||
refresh = true;
|
refresh = true;
|
||||||
break;
|
break;
|
||||||
case BRIGHTNESS_CYCLE_REVERSE:
|
case BRIGHTNESS_CYCLE_REVERSE:
|
||||||
PIDisplay.INSTANCE.setScreen(new MarioScreen()); //TODO: rimuovere: prova
|
DisplayManager.INSTANCE.setScreen(new MarioScreen()); //TODO: rimuovere: prova
|
||||||
PIDisplay.cycleBrightness(true);
|
DisplayManager.cycleBrightness(true);
|
||||||
refresh = true;
|
refresh = true;
|
||||||
break;
|
break;
|
||||||
case HISTORY_BACK:
|
case HISTORY_BACK:
|
||||||
PIDisplay.INSTANCE.goBack();
|
DisplayManager.INSTANCE.goBack();
|
||||||
refresh = true;
|
refresh = true;
|
||||||
break;
|
break;
|
||||||
case HISTORY_FORWARD:
|
case HISTORY_FORWARD:
|
||||||
PIDisplay.INSTANCE.goForward();
|
DisplayManager.INSTANCE.goForward();
|
||||||
refresh = true;
|
refresh = true;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
@ -736,7 +748,7 @@ public class Keyboard {
|
|||||||
refresh = true;
|
refresh = true;
|
||||||
}
|
}
|
||||||
if (refresh) {
|
if (refresh) {
|
||||||
PIDisplay.display.repaint();
|
// PIDisplay.display.repaint();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -747,9 +759,9 @@ public class Keyboard {
|
|||||||
|
|
||||||
public static void keyReleased(Key k) {
|
public static void keyReleased(Key k) {
|
||||||
boolean refresh = false;
|
boolean refresh = false;
|
||||||
if (PIDisplay.INSTANCE != null) {
|
if (DisplayManager.INSTANCE != null) {
|
||||||
Screen scr = PIDisplay.INSTANCE.getScreen();
|
final Screen scr = DisplayManager.INSTANCE.getScreen();
|
||||||
if(scr != null && scr.initialized && scr.keyReleased(k)) {
|
if (scr != null && scr.initialized && scr.keyReleased(k)) {
|
||||||
refresh = true;
|
refresh = true;
|
||||||
} else {
|
} else {
|
||||||
switch (k) {
|
switch (k) {
|
||||||
@ -760,26 +772,17 @@ public class Keyboard {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (refresh) {
|
if (refresh) {
|
||||||
PIDisplay.display.repaint();
|
// PIDisplay.display.repaint();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static enum Key {
|
public static enum Key {
|
||||||
POWER, debug_DEG, debug_RAD, debug_GRA, SHIFT, ALPHA, NONE,
|
POWER, debug_DEG, debug_RAD, debug_GRA, SHIFT, ALPHA, NONE, HISTORY_BACK, HISTORY_FORWARD, SURD_MODE, DRG_CYCLE, LETTER_X, LETTER_Y, SIMPLIFY, SOLVE, BRIGHTNESS_CYCLE, BRIGHTNESS_CYCLE_REVERSE, DOT, NUM0, NUM1, NUM2, NUM3, NUM4, NUM5, NUM6, NUM7, NUM8, NUM9, PARENTHESIS_OPEN, PARENTHESIS_CLOSE, PLUS, MINUS, PLUS_MINUS, MULTIPLY, DIVIDE, EQUAL, DELETE, RESET, LEFT, RIGHT, UP, DOWN, OK, debug1, debug2, debug3, debug4, debug5, SQRT, ROOT, POWER_OF_2, POWER_OF_x, SINE, COSINE, TANGENT, ARCSINE, ARCCOSINE, ARCTANGENT, PI
|
||||||
HISTORY_BACK, HISTORY_FORWARD, SURD_MODE, DRG_CYCLE,
|
|
||||||
LETTER_X, LETTER_Y, SIMPLIFY, SOLVE, BRIGHTNESS_CYCLE,
|
|
||||||
BRIGHTNESS_CYCLE_REVERSE, DOT, NUM0, NUM1, NUM2, NUM3, NUM4, NUM5, NUM6, NUM7, NUM8, NUM9,
|
|
||||||
PARENTHESIS_OPEN, PARENTHESIS_CLOSE, PLUS, MINUS, PLUS_MINUS, MULTIPLY, DIVIDE, EQUAL,
|
|
||||||
DELETE, RESET, LEFT, RIGHT, UP, DOWN, OK, debug1, debug2, debug3, debug4, debug5,
|
|
||||||
SQRT, ROOT, POWER_OF_2, POWER_OF_x,
|
|
||||||
SINE, COSINE, TANGENT, ARCSINE, ARCCOSINE, ARCTANGENT, PI
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
||||||
|
|
||||||
|
@ -4,10 +4,10 @@ import com.pi4j.wiringpi.Gpio;
|
|||||||
|
|
||||||
public class ParallelToSerial {
|
public class ParallelToSerial {
|
||||||
|
|
||||||
private int SH_LD;
|
private final int SH_LD;
|
||||||
private int CLK_INH;
|
private final int CLK_INH;
|
||||||
private int QH;
|
private final int QH;
|
||||||
private int CLK;
|
private final int CLK;
|
||||||
|
|
||||||
public ParallelToSerial(int SH_LD_pin, int CLK_INH_pin, int QH_pin, int CLK_pin) {
|
public ParallelToSerial(int SH_LD_pin, int CLK_INH_pin, int QH_pin, int CLK_pin) {
|
||||||
SH_LD = SH_LD_pin;
|
SH_LD = SH_LD_pin;
|
||||||
@ -17,7 +17,7 @@ public class ParallelToSerial {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public boolean[] read() {
|
public boolean[] read() {
|
||||||
boolean[] data = new boolean[8];
|
final boolean[] data = new boolean[8];
|
||||||
Gpio.digitalWrite(CLK_INH, Gpio.HIGH);
|
Gpio.digitalWrite(CLK_INH, Gpio.HIGH);
|
||||||
Gpio.digitalWrite(SH_LD, Gpio.LOW);
|
Gpio.digitalWrite(SH_LD, Gpio.LOW);
|
||||||
Gpio.delay(1);
|
Gpio.delay(1);
|
||||||
@ -27,7 +27,7 @@ public class ParallelToSerial {
|
|||||||
for (int i = 7; i >= 0; i--) {
|
for (int i = 7; i >= 0; i--) {
|
||||||
Gpio.digitalWrite(CLK, Gpio.HIGH);
|
Gpio.digitalWrite(CLK, Gpio.HIGH);
|
||||||
Gpio.digitalWrite(CLK, Gpio.LOW);
|
Gpio.digitalWrite(CLK, Gpio.LOW);
|
||||||
data[i] = Gpio.digitalRead(QH)==Gpio.HIGH?true:false;
|
data[i] = Gpio.digitalRead(QH) == Gpio.HIGH ? true : false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return data;
|
return data;
|
||||||
|
@ -3,9 +3,9 @@ package org.warp.picalculator.device.chip;
|
|||||||
import com.pi4j.wiringpi.Gpio;
|
import com.pi4j.wiringpi.Gpio;
|
||||||
|
|
||||||
public class SerialToParallel {
|
public class SerialToParallel {
|
||||||
private int RCK; //Storage register clock pin (latch pin)
|
private final int RCK; //Storage register clock pin (latch pin)
|
||||||
private int SCK; //Shift register clock pin
|
private final int SCK; //Shift register clock pin
|
||||||
private int SER; //Serial data input
|
private final int SER; //Serial data input
|
||||||
|
|
||||||
public SerialToParallel(int RCK_pin, int SCK_pin, int SER_pin) {
|
public SerialToParallel(int RCK_pin, int SCK_pin, int SER_pin) {
|
||||||
RCK = RCK_pin;
|
RCK = RCK_pin;
|
||||||
|
494
src/org/warp/picalculator/gui/DisplayManager.java
Normal file
494
src/org/warp/picalculator/gui/DisplayManager.java
Normal file
@ -0,0 +1,494 @@
|
|||||||
|
package org.warp.picalculator.gui;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.lang.management.ManagementFactory;
|
||||||
|
import java.lang.management.OperatingSystemMXBean;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.lang.reflect.Modifier;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
|
||||||
|
import org.warp.picalculator.Main;
|
||||||
|
import org.warp.picalculator.Utils;
|
||||||
|
import org.warp.picalculator.device.Keyboard;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Drawable;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Renderer;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.gpu.GPUDisplay;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
|
import org.warp.picalculator.gui.screens.Screen;
|
||||||
|
|
||||||
|
import com.pi4j.wiringpi.Gpio;
|
||||||
|
|
||||||
|
public final class DisplayManager implements Drawable {
|
||||||
|
public static DisplayManager INSTANCE;
|
||||||
|
private static float brightness;
|
||||||
|
|
||||||
|
public static final Display display = chooseGraphicEngine();
|
||||||
|
public static Renderer renderer;
|
||||||
|
|
||||||
|
private static RAWSkin skin;
|
||||||
|
public static RAWFont[] fonts;
|
||||||
|
|
||||||
|
public static String error = null;
|
||||||
|
public String[] errorStackTrace = null;
|
||||||
|
public final static int[] glyphsHeight = new int[] { 9, 6, 12, 9 };
|
||||||
|
|
||||||
|
public static Screen screen;
|
||||||
|
public static String displayDebugString = "";
|
||||||
|
|
||||||
|
public DisplayManager(Screen screen) {
|
||||||
|
setScreen(screen);
|
||||||
|
INSTANCE = this;
|
||||||
|
loop();
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
* private void load_skin() {
|
||||||
|
* try {
|
||||||
|
* skin_tex = glGenTextures();
|
||||||
|
* glBindTexture(GL_TEXTURE_2D, skin_tex);
|
||||||
|
* glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
|
||||||
|
*
|
||||||
|
* InputStream in = new FileInputStream("skin.png");
|
||||||
|
* PNGDecoder decoder = new PNGDecoder(in);
|
||||||
|
*
|
||||||
|
* System.out.println("width="+decoder.getWidth());
|
||||||
|
* System.out.println("height="+decoder.getHeight());
|
||||||
|
*
|
||||||
|
* ByteBuffer buf =
|
||||||
|
* ByteBuffer.allocateDirect(4*decoder.getWidth()*decoder.getHeight());
|
||||||
|
* decoder.decode(buf, decoder.getWidth()*4, Format.RGBA);
|
||||||
|
* buf.flip();
|
||||||
|
*
|
||||||
|
* skin = buf;
|
||||||
|
* skin_w = decoder.getWidth();
|
||||||
|
* skin_h = decoder.getHeight();
|
||||||
|
* glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, skin_w,
|
||||||
|
* skin_h, 0, GL_RGBA, GL_UNSIGNED_BYTE, skin);
|
||||||
|
* } catch (IOException ex) {
|
||||||
|
* ex.printStackTrace();
|
||||||
|
* }
|
||||||
|
* }
|
||||||
|
*/
|
||||||
|
|
||||||
|
private static Display chooseGraphicEngine() {
|
||||||
|
Display d;
|
||||||
|
d = new GPUDisplay();
|
||||||
|
if (d.isSupported()) return d;
|
||||||
|
d = new CPUDisplay();
|
||||||
|
if (d.isSupported()) return d;
|
||||||
|
throw new UnsupportedOperationException("No graphic engines available.");
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setScreen(Screen screen) {
|
||||||
|
if (screen.initialized == false) {
|
||||||
|
if (screen.canBeInHistory) {
|
||||||
|
DisplayManager.currentSession = 0;
|
||||||
|
for (int i = DisplayManager.sessions.length - 1; i >= 1; i--) {
|
||||||
|
DisplayManager.sessions[i] = DisplayManager.sessions[i - 1];
|
||||||
|
}
|
||||||
|
DisplayManager.sessions[0] = screen;
|
||||||
|
} else {
|
||||||
|
DisplayManager.currentSession = -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen.d = this;
|
||||||
|
try {
|
||||||
|
screen.create();
|
||||||
|
DisplayManager.screen = screen;
|
||||||
|
if (screen.initialized == false) {
|
||||||
|
screen.initialize();
|
||||||
|
}
|
||||||
|
} catch (final Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
System.exit(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void replaceScreen(Screen screen) {
|
||||||
|
if (screen.initialized == false) {
|
||||||
|
if (screen.canBeInHistory) {
|
||||||
|
DisplayManager.sessions[DisplayManager.currentSession] = screen;
|
||||||
|
} else {
|
||||||
|
DisplayManager.currentSession = -1;
|
||||||
|
for (int i = 0; i < DisplayManager.sessions.length - 2; i++) {
|
||||||
|
DisplayManager.sessions[i] = DisplayManager.sessions[i + 1];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
screen.d = this;
|
||||||
|
try {
|
||||||
|
screen.create();
|
||||||
|
DisplayManager.screen = screen;
|
||||||
|
if (screen.initialized == false) {
|
||||||
|
screen.initialize();
|
||||||
|
}
|
||||||
|
} catch (final Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
System.exit(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean canGoBack() {
|
||||||
|
if (DisplayManager.currentSession == -1) {
|
||||||
|
return DisplayManager.sessions[0] != null;
|
||||||
|
}
|
||||||
|
if (DisplayManager.screen != DisplayManager.sessions[DisplayManager.currentSession]) {
|
||||||
|
|
||||||
|
} else if (DisplayManager.currentSession + 1 < DisplayManager.sessions.length) {
|
||||||
|
if (DisplayManager.sessions[DisplayManager.currentSession + 1] != null) {
|
||||||
|
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (DisplayManager.sessions[DisplayManager.currentSession] != null) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void goBack() {
|
||||||
|
if (canGoBack()) {
|
||||||
|
if (DisplayManager.currentSession >= 0 && DisplayManager.screen != DisplayManager.sessions[DisplayManager.currentSession]) {} else {
|
||||||
|
DisplayManager.currentSession += 1;
|
||||||
|
}
|
||||||
|
DisplayManager.screen = DisplayManager.sessions[DisplayManager.currentSession];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean canGoForward() {
|
||||||
|
if (DisplayManager.currentSession <= 0) { // -1 e 0
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (DisplayManager.screen != DisplayManager.sessions[DisplayManager.currentSession]) {
|
||||||
|
|
||||||
|
} else if (DisplayManager.currentSession > 0) {
|
||||||
|
if (DisplayManager.sessions[DisplayManager.currentSession - 1] != null) {
|
||||||
|
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
if (DisplayManager.sessions[DisplayManager.currentSession] != null) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void goForward() {
|
||||||
|
if (canGoForward()) {
|
||||||
|
if (DisplayManager.screen != DisplayManager.sessions[DisplayManager.currentSession]) {
|
||||||
|
|
||||||
|
} else {
|
||||||
|
DisplayManager.currentSession -= 1;
|
||||||
|
}
|
||||||
|
DisplayManager.screen = DisplayManager.sessions[DisplayManager.currentSession];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public Screen getScreen() {
|
||||||
|
return DisplayManager.screen;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void load_skin() throws IOException {
|
||||||
|
skin = display.loadSkin("skin.png");
|
||||||
|
}
|
||||||
|
|
||||||
|
private void load_fonts() throws IOException {
|
||||||
|
fonts = new RAWFont[7];
|
||||||
|
fonts[0] = display.loadFont("big");
|
||||||
|
fonts[1] = display.loadFont("small");
|
||||||
|
fonts[2] = display.loadFont("ex");
|
||||||
|
fonts[3] = display.loadFont("big");
|
||||||
|
fonts[4] = display.loadFont("32");
|
||||||
|
fonts[5] = display.loadFont("square");
|
||||||
|
}
|
||||||
|
|
||||||
|
private void draw_init() {
|
||||||
|
renderer.glClear(display.getWidth(), display.getHeight());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void draw_status() {
|
||||||
|
renderer.glColor(0xFFc5c2af);
|
||||||
|
renderer.glFillColor(0, 0, display.getWidth(), 20);
|
||||||
|
renderer.glColor3i(0, 0, 0);
|
||||||
|
renderer.glDrawLine(0, 20, display.getWidth() - 1, 20);
|
||||||
|
renderer.glColor3i(255, 255, 255);
|
||||||
|
skin.use(display);
|
||||||
|
if (Keyboard.shift) {
|
||||||
|
renderer.glFillRect(2 + 18 * 0, 2, 16, 16, 16 * 2, 16 * 0, 16, 16);
|
||||||
|
} else {
|
||||||
|
renderer.glFillRect(2 + 18 * 0, 2, 16, 16, 16 * 3, 16 * 0, 16, 16);
|
||||||
|
}
|
||||||
|
if (Keyboard.alpha) {
|
||||||
|
renderer.glFillRect(2 + 18 * 1, 2, 16, 16, 16 * 0, 16 * 0, 16, 16);
|
||||||
|
} else {
|
||||||
|
renderer.glFillRect(2 + 18 * 1, 2, 16, 16, 16 * 1, 16 * 0, 16, 16);
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
if (Calculator.angleMode == AngleMode.DEG) {
|
||||||
|
drawSkinPart(8 + 18 * 2, 2, 16 * 4, 16 * 0, 16 + 16 * 4, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 3, 2, 16 * 7, 16 * 0, 16 + 16 * 7, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 4, 2, 16 * 9, 16 * 0, 16 + 16 * 9, 16 + 16 * 0);
|
||||||
|
} else if (Calculator.angleMode == AngleMode.RAD) {
|
||||||
|
drawSkinPart(8 + 18 * 2, 2, 16 * 5, 16 * 0, 16 + 16 * 5, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 3, 2, 16 * 6, 16 * 0, 16 + 16 * 6, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 4, 2, 16 * 9, 16 * 0, 16 + 16 * 9, 16 + 16 * 0);
|
||||||
|
} else if (Calculator.angleMode == AngleMode.GRA) {
|
||||||
|
drawSkinPart(8 + 18 * 2, 2, 16 * 5, 16 * 0, 16 + 16 * 5, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 3, 2, 16 * 7, 16 * 0, 16 + 16 * 7, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 4, 2, 16 * 8, 16 * 0, 16 + 16 * 8, 16 + 16 * 0);
|
||||||
|
} else {
|
||||||
|
drawSkinPart(8 + 18 * 2, 2, 16 * 5, 16 * 0, 16 + 16 * 5, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 3, 2, 16 * 7, 16 * 0, 16 + 16 * 7, 16 + 16 * 0);
|
||||||
|
drawSkinPart(8 + 18 * 4, 2, 16 * 9, 16 * 0, 16 + 16 * 9, 16 + 16 * 0);
|
||||||
|
}*/
|
||||||
|
|
||||||
|
int padding = 2;
|
||||||
|
|
||||||
|
final int brightness = (int) (Math.ceil(DisplayManager.brightness * 9));
|
||||||
|
if (brightness <= 10) {
|
||||||
|
renderer.glFillRect(Main.screenSize[0] - (padding + 16), 2, 16, 16, 16 * brightness, 16 * 1, 16, 16);
|
||||||
|
} else {
|
||||||
|
Utils.debug.println("Brightness error");
|
||||||
|
}
|
||||||
|
|
||||||
|
padding += 18 + 6;
|
||||||
|
|
||||||
|
final boolean canGoBack = canGoBack();
|
||||||
|
final boolean canGoForward = canGoForward();
|
||||||
|
|
||||||
|
if (Main.haxMode) {
|
||||||
|
renderer.glFillRect(Main.screenSize[0] - (padding + 16), 2, 16, 16, 16 * 18, 16 * 0, 16, 16);
|
||||||
|
padding += 18 + 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (canGoBack && canGoForward) {
|
||||||
|
renderer.glFillRect(Main.screenSize[0] - (padding + 16), 2, 16, 16, 16 * 14, 16 * 0, 16, 16);
|
||||||
|
} else if (canGoBack) {
|
||||||
|
renderer.glFillRect(Main.screenSize[0] - (padding + 16), 2, 16, 16, 16 * 15, 16 * 0, 16, 16);
|
||||||
|
} else if (canGoForward) {
|
||||||
|
renderer.glFillRect(Main.screenSize[0] - (padding + 16), 2, 16, 16, 16 * 16, 16 * 0, 16, 16);
|
||||||
|
} else {
|
||||||
|
renderer.glFillRect(Main.screenSize[0] - (padding + 16), 2, 16, 16, 16 * 17, 16 * 0, 16, 16);
|
||||||
|
}
|
||||||
|
|
||||||
|
padding += 18;
|
||||||
|
|
||||||
|
screen.renderStatusbar();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void draw_screen() {
|
||||||
|
screen.render();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void draw_bottom() {
|
||||||
|
renderer.glDrawStringLeft(2, 90, displayDebugString);
|
||||||
|
|
||||||
|
Utils.getFont(false, true).use(DisplayManager.display);
|
||||||
|
DisplayManager.renderer.glColor4i(255, 0, 0, 40);
|
||||||
|
DisplayManager.renderer.glDrawStringLeft(5 + 1, Main.screenSize[1] - 20 + 1, "WORK IN PROGRESS.");
|
||||||
|
DisplayManager.renderer.glColor4i(255, 0, 0, 80);
|
||||||
|
DisplayManager.renderer.glDrawStringLeft(5, Main.screenSize[1] - 20, "WORK IN PROGRESS.");
|
||||||
|
}
|
||||||
|
|
||||||
|
private void draw_world() {
|
||||||
|
renderer.glColor3i(255, 255, 255);
|
||||||
|
|
||||||
|
if (error != null) {
|
||||||
|
Utils.getFont(false, false).use(display);
|
||||||
|
renderer.glColor3i(129, 28, 22);
|
||||||
|
renderer.glDrawStringRight(Main.screenSize[0] - 2, Main.screenSize[1] - DisplayManager.glyphsHeight[1] - 2, "ANDREA CAVALLI'S CALCULATOR");
|
||||||
|
renderer.glColor3i(149, 32, 26);
|
||||||
|
renderer.glDrawStringCenter((Main.screenSize[0] / 2), 22, error);
|
||||||
|
renderer.glColor3i(164, 34, 28);
|
||||||
|
int i = 22;
|
||||||
|
for (final String stackPart : errorStackTrace) {
|
||||||
|
renderer.glDrawStringLeft(2, 22 + i, stackPart);
|
||||||
|
i += 11;
|
||||||
|
}
|
||||||
|
fonts[0].use(display);
|
||||||
|
renderer.glColor3i(129, 28, 22);
|
||||||
|
renderer.glDrawStringCenter((Main.screenSize[0] / 2), 11, "UNEXPECTED EXCEPTION");
|
||||||
|
} else {
|
||||||
|
fonts[0].use(display);
|
||||||
|
draw_screen();
|
||||||
|
draw_status();
|
||||||
|
draw_bottom();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void draw() {
|
||||||
|
draw_init();
|
||||||
|
draw_world();
|
||||||
|
}
|
||||||
|
|
||||||
|
private long precTime = -1;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void refresh() {
|
||||||
|
float dt = 0;
|
||||||
|
final long newtime = System.nanoTime();
|
||||||
|
if (precTime == -1) {
|
||||||
|
dt = 0;
|
||||||
|
} else {
|
||||||
|
dt = (float) ((newtime - precTime) / 1000000000d);
|
||||||
|
}
|
||||||
|
precTime = newtime;
|
||||||
|
/*
|
||||||
|
* Calcoli
|
||||||
|
*/
|
||||||
|
checkDisplayResized();
|
||||||
|
|
||||||
|
screen.beforeRender(dt);
|
||||||
|
|
||||||
|
if (dt >= 0.03 || screen.mustBeRefreshed()) {
|
||||||
|
draw();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private void checkDisplayResized() {
|
||||||
|
if (display.wasResized()) {
|
||||||
|
Main.screenSize[0] = display.getWidth();
|
||||||
|
Main.screenSize[1] = display.getHeight();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
public void loop() {
|
||||||
|
try {
|
||||||
|
load_skin();
|
||||||
|
load_fonts();
|
||||||
|
display.create();
|
||||||
|
renderer = display.getRenderer();
|
||||||
|
|
||||||
|
try {
|
||||||
|
screen.initialize();
|
||||||
|
} catch (final Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
System.exit(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
//Debug thread
|
||||||
|
Thread dbgthrd = new Thread(() -> {
|
||||||
|
try {
|
||||||
|
while (true) {
|
||||||
|
for (int i = 0; i < 10; i++) {
|
||||||
|
System.out.println("============");
|
||||||
|
OperatingSystemMXBean operatingSystemMXBean = ManagementFactory.getOperatingSystemMXBean();
|
||||||
|
for (Method method : operatingSystemMXBean.getClass().getDeclaredMethods()) {
|
||||||
|
method.setAccessible(true);
|
||||||
|
if (method.getName().startsWith("get") && Modifier.isPublic(method.getModifiers())) {
|
||||||
|
Object value;
|
||||||
|
try {
|
||||||
|
value = method.invoke(operatingSystemMXBean);
|
||||||
|
} catch (Exception e) {
|
||||||
|
value = e;
|
||||||
|
} // try
|
||||||
|
boolean percent = false;
|
||||||
|
boolean mb = false;
|
||||||
|
String displayName = method.getName();
|
||||||
|
String displayValue = value.toString();
|
||||||
|
if (displayName.endsWith("CpuLoad")) {
|
||||||
|
percent = true;
|
||||||
|
}
|
||||||
|
if (displayName.endsWith("MemorySize")) {
|
||||||
|
mb = true;
|
||||||
|
}
|
||||||
|
ArrayList<String> arr = new ArrayList<>();
|
||||||
|
arr.add("getFreePhysicalMemorySize");
|
||||||
|
arr.add("getProcessCpuLoad");
|
||||||
|
arr.add("getSystemCpuLoad");
|
||||||
|
arr.add("getTotalPhysicalMemorySize");
|
||||||
|
if (arr.contains(displayName)) {
|
||||||
|
if (percent) {
|
||||||
|
try {
|
||||||
|
System.out.println(displayName + " = " + (((int)(Float.parseFloat(displayValue) * 10000f))/100f) + "%");
|
||||||
|
}catch(Exception ex) {
|
||||||
|
System.out.println(displayName + " = " + displayValue);
|
||||||
|
}
|
||||||
|
} else if (mb) {
|
||||||
|
try {
|
||||||
|
System.out.println(displayName + " = " + (Long.parseLong(displayValue) / 1024L / 1024L) + " MB");
|
||||||
|
}catch(Exception ex) {
|
||||||
|
System.out.println(displayName + " = " + displayValue);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
System.out.println(displayName + " = " + displayValue);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} // if
|
||||||
|
} // for
|
||||||
|
System.out.println("============");
|
||||||
|
Thread.sleep(5000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (final InterruptedException e) {
|
||||||
|
// TODO Auto-generated catch block
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
dbgthrd.setDaemon(true);
|
||||||
|
dbgthrd.setName("Debug performance thread");
|
||||||
|
dbgthrd.start();
|
||||||
|
|
||||||
|
display.start(this);
|
||||||
|
|
||||||
|
display.waitUntilExit();
|
||||||
|
} catch (final Exception ex) {
|
||||||
|
ex.printStackTrace();
|
||||||
|
} finally {}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void changeBrightness(float change) {
|
||||||
|
setBrightness(brightness + change);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void setBrightness(float newval) {
|
||||||
|
if (newval >= 0 && newval <= 1) {
|
||||||
|
brightness = newval;
|
||||||
|
if (Utils.debugOn == false) {
|
||||||
|
Gpio.pwmWrite(12, (int) Math.ceil(brightness * 1024));
|
||||||
|
// SoftPwm.softPwmWrite(12, (int)(Math.ceil(brightness*10)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void cycleBrightness(boolean reverse) {
|
||||||
|
final float step = reverse ? -0.1f : 0.1f;
|
||||||
|
if (brightness + step > 1f) {
|
||||||
|
setBrightness(0f);
|
||||||
|
} else if (brightness + step <= 0f) {
|
||||||
|
setBrightness(1.0f);
|
||||||
|
} else {
|
||||||
|
changeBrightness(step);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static float getBrightness() {
|
||||||
|
return brightness;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int currentSession = 0;
|
||||||
|
public static Screen[] sessions = new Screen[5];
|
||||||
|
|
||||||
|
@Deprecated
|
||||||
|
public static void colore(float f1, float f2, float f3, float f4) {
|
||||||
|
renderer.glColor4f(f1,f2,f3,f4);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Drawable getDrawable() {
|
||||||
|
return INSTANCE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Deprecated
|
||||||
|
public static void drawSkinPart(int x, int y, int uvX, int uvY, int uvX2, int uvY2) {
|
||||||
|
renderer.glFillRect(x, y, uvX2-uvX, uvY2-uvY, uvX, uvY, uvX2-uvX, uvY2-uvY);
|
||||||
|
}
|
||||||
|
}
|
60
src/org/warp/picalculator/gui/GraphicUtils.java
Normal file
60
src/org/warp/picalculator/gui/GraphicUtils.java
Normal file
@ -0,0 +1,60 @@
|
|||||||
|
package org.warp.picalculator.gui;
|
||||||
|
|
||||||
|
public class GraphicUtils {
|
||||||
|
public static final float sin(float rad)
|
||||||
|
{
|
||||||
|
return sin[(int) (rad * radToIndex) & SIN_MASK];
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final float cos(float rad)
|
||||||
|
{
|
||||||
|
return cos[(int) (rad * radToIndex) & SIN_MASK];
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final float sinDeg(float deg)
|
||||||
|
{
|
||||||
|
return sin[(int) (deg * degToIndex) & SIN_MASK];
|
||||||
|
}
|
||||||
|
|
||||||
|
public static final float cosDeg(float deg)
|
||||||
|
{
|
||||||
|
return cos[(int) (deg * degToIndex) & SIN_MASK];
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final float RAD,DEG;
|
||||||
|
private static final int SIN_BITS,SIN_MASK,SIN_COUNT;
|
||||||
|
private static final float radFull,radToIndex;
|
||||||
|
private static final float degFull,degToIndex;
|
||||||
|
private static final float[] sin, cos;
|
||||||
|
|
||||||
|
static
|
||||||
|
{
|
||||||
|
RAD = (float) Math.PI / 180.0f;
|
||||||
|
DEG = 180.0f / (float) Math.PI;
|
||||||
|
|
||||||
|
SIN_BITS = 12;
|
||||||
|
SIN_MASK = ~(-1 << SIN_BITS);
|
||||||
|
SIN_COUNT = SIN_MASK + 1;
|
||||||
|
|
||||||
|
radFull = (float) (Math.PI * 2.0);
|
||||||
|
degFull = (float) (360.0);
|
||||||
|
radToIndex = SIN_COUNT / radFull;
|
||||||
|
degToIndex = SIN_COUNT / degFull;
|
||||||
|
|
||||||
|
sin = new float[SIN_COUNT];
|
||||||
|
cos = new float[SIN_COUNT];
|
||||||
|
|
||||||
|
for (int i = 0; i < SIN_COUNT; i++)
|
||||||
|
{
|
||||||
|
sin[i] = (float) Math.sin((i + 0.5f) / SIN_COUNT * radFull);
|
||||||
|
cos[i] = (float) Math.cos((i + 0.5f) / SIN_COUNT * radFull);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Four cardinal directions (credits: Nate)
|
||||||
|
for (int i = 0; i < 360; i += 90)
|
||||||
|
{
|
||||||
|
sin[(int)(i * degToIndex) & SIN_MASK] = (float)Math.sin(i * Math.PI / 180.0);
|
||||||
|
cos[(int)(i * degToIndex) & SIN_MASK] = (float)Math.cos(i * Math.PI / 180.0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,437 +0,0 @@
|
|||||||
package org.warp.picalculator.gui;
|
|
||||||
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
import javax.imageio.ImageIO;
|
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
|
||||||
import org.warp.picalculator.Utils;
|
|
||||||
import org.warp.picalculator.device.Keyboard;
|
|
||||||
import org.warp.picalculator.gui.graphicengine.Display;
|
|
||||||
import org.warp.picalculator.gui.graphicengine.Drawable;
|
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
|
||||||
import org.warp.picalculator.gui.graphicengine.Renderer;
|
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
|
||||||
import org.warp.picalculator.gui.screens.Screen;
|
|
||||||
|
|
||||||
import com.pi4j.wiringpi.Gpio;
|
|
||||||
|
|
||||||
public final class PIDisplay implements Drawable {
|
|
||||||
public static PIDisplay INSTANCE;
|
|
||||||
private static float brightness;
|
|
||||||
|
|
||||||
public static final Display display = new CPUDisplay();
|
|
||||||
public static final Renderer renderer = display.getRenderer();
|
|
||||||
|
|
||||||
private static int[] skin;
|
|
||||||
private static int[] skinSize;
|
|
||||||
public static RAWFont[] fonts;
|
|
||||||
|
|
||||||
public static String error = null;
|
|
||||||
public String[] errorStackTrace = null;
|
|
||||||
public final static int[] glyphsHeight = new int[] { 9, 6, 12, 9 };
|
|
||||||
|
|
||||||
public static Screen screen;
|
|
||||||
public static String displayDebugString = "";
|
|
||||||
|
|
||||||
public PIDisplay(Screen screen) {
|
|
||||||
setScreen(screen);
|
|
||||||
INSTANCE = this;
|
|
||||||
loop();
|
|
||||||
}
|
|
||||||
/*
|
|
||||||
* private void load_skin() {
|
|
||||||
* try {
|
|
||||||
* skin_tex = glGenTextures();
|
|
||||||
* glBindTexture(GL_TEXTURE_2D, skin_tex);
|
|
||||||
* glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
|
|
||||||
*
|
|
||||||
* InputStream in = new FileInputStream("skin.png");
|
|
||||||
* PNGDecoder decoder = new PNGDecoder(in);
|
|
||||||
*
|
|
||||||
* System.out.println("width="+decoder.getWidth());
|
|
||||||
* System.out.println("height="+decoder.getHeight());
|
|
||||||
*
|
|
||||||
* ByteBuffer buf =
|
|
||||||
* ByteBuffer.allocateDirect(4*decoder.getWidth()*decoder.getHeight());
|
|
||||||
* decoder.decode(buf, decoder.getWidth()*4, Format.RGBA);
|
|
||||||
* buf.flip();
|
|
||||||
*
|
|
||||||
* skin = buf;
|
|
||||||
* skin_w = decoder.getWidth();
|
|
||||||
* skin_h = decoder.getHeight();
|
|
||||||
* glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, skin_w,
|
|
||||||
* skin_h, 0, GL_RGBA, GL_UNSIGNED_BYTE, skin);
|
|
||||||
* } catch (IOException ex) {
|
|
||||||
* ex.printStackTrace();
|
|
||||||
* }
|
|
||||||
* }
|
|
||||||
*/
|
|
||||||
|
|
||||||
public void setScreen(Screen screen) {
|
|
||||||
if (screen.initialized == false) {
|
|
||||||
if (screen.canBeInHistory) {
|
|
||||||
PIDisplay.currentSession = 0;
|
|
||||||
for (int i = PIDisplay.sessions.length - 1; i >= 1; i--) {
|
|
||||||
PIDisplay.sessions[i] = PIDisplay.sessions[i - 1];
|
|
||||||
}
|
|
||||||
PIDisplay.sessions[0] = screen;
|
|
||||||
} else {
|
|
||||||
PIDisplay.currentSession = -1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
screen.d = this;
|
|
||||||
try {
|
|
||||||
screen.create();
|
|
||||||
PIDisplay.screen = screen;
|
|
||||||
if (screen.initialized == false) {
|
|
||||||
screen.initialize();
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
System.exit(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void replaceScreen(Screen screen) {
|
|
||||||
if (screen.initialized == false) {
|
|
||||||
if (screen.canBeInHistory) {
|
|
||||||
PIDisplay.sessions[PIDisplay.currentSession] = screen;
|
|
||||||
} else {
|
|
||||||
PIDisplay.currentSession = -1;
|
|
||||||
for (int i = 0; i < PIDisplay.sessions.length - 2; i++) {
|
|
||||||
PIDisplay.sessions[i] = PIDisplay.sessions[i + 1];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
screen.d = this;
|
|
||||||
try {
|
|
||||||
screen.create();
|
|
||||||
PIDisplay.screen = screen;
|
|
||||||
if (screen.initialized == false) {
|
|
||||||
screen.initialize();
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
System.exit(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean canGoBack() {
|
|
||||||
if (PIDisplay.currentSession == -1) {
|
|
||||||
return PIDisplay.sessions[0] != null;
|
|
||||||
}
|
|
||||||
if (PIDisplay.screen != PIDisplay.sessions[PIDisplay.currentSession]) {
|
|
||||||
|
|
||||||
} else if (PIDisplay.currentSession + 1 < PIDisplay.sessions.length) {
|
|
||||||
if (PIDisplay.sessions[PIDisplay.currentSession + 1] != null) {
|
|
||||||
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (PIDisplay.sessions[PIDisplay.currentSession] != null) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void goBack() {
|
|
||||||
if (canGoBack()) {
|
|
||||||
if (PIDisplay.currentSession >= 0 && PIDisplay.screen != PIDisplay.sessions[PIDisplay.currentSession]) {
|
|
||||||
} else {
|
|
||||||
PIDisplay.currentSession += 1;
|
|
||||||
}
|
|
||||||
PIDisplay.screen = PIDisplay.sessions[PIDisplay.currentSession];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean canGoForward() {
|
|
||||||
if (PIDisplay.currentSession <= 0) { // -1 e 0
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (PIDisplay.screen != PIDisplay.sessions[PIDisplay.currentSession]) {
|
|
||||||
|
|
||||||
} else if (PIDisplay.currentSession > 0) {
|
|
||||||
if (PIDisplay.sessions[PIDisplay.currentSession - 1] != null) {
|
|
||||||
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (PIDisplay.sessions[PIDisplay.currentSession] != null) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void goForward() {
|
|
||||||
if (canGoForward()) {
|
|
||||||
if (PIDisplay.screen != PIDisplay.sessions[PIDisplay.currentSession]) {
|
|
||||||
|
|
||||||
} else {
|
|
||||||
PIDisplay.currentSession -= 1;
|
|
||||||
}
|
|
||||||
PIDisplay.screen = PIDisplay.sessions[PIDisplay.currentSession];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public Screen getScreen() {
|
|
||||||
return PIDisplay.screen;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void load_skin() throws IOException {
|
|
||||||
BufferedImage img = ImageIO.read(Main.instance.getClass().getResource("/skin.png"));
|
|
||||||
skin = renderer.getMatrixOfImage(img);
|
|
||||||
skinSize = new int[] { img.getWidth(), img.getHeight() };
|
|
||||||
}
|
|
||||||
|
|
||||||
private void load_fonts() {
|
|
||||||
fonts = new RAWFont[7];
|
|
||||||
fonts[0] = new RAWFont();
|
|
||||||
fonts[0].create("big");
|
|
||||||
fonts[1] = new RAWFont();
|
|
||||||
fonts[1].create("small");
|
|
||||||
fonts[2] = new RAWFont();
|
|
||||||
fonts[2].create("ex");
|
|
||||||
fonts[3] = new RAWFont();
|
|
||||||
fonts[3].create("big");
|
|
||||||
fonts[4] = new RAWFont();
|
|
||||||
fonts[4].create("32");
|
|
||||||
fonts[5] = new RAWFont();
|
|
||||||
fonts[5].create("square");
|
|
||||||
renderer.glSetFont(fonts[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void draw_init() {
|
|
||||||
renderer.glClear();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void drawSkinPart(int x, int y, int sx1, int sy1, int sx2, int sy2) {
|
|
||||||
renderer.glDrawSkin(skinSize[0], skin, x, y, sx1, sy1, sx2, sy2, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void draw_status() {
|
|
||||||
renderer.glColor(0xFFc5c2af);
|
|
||||||
renderer.glFillRect(0, 0, Main.screenSize[0], 20);
|
|
||||||
renderer.glColor3i(0, 0, 0);
|
|
||||||
renderer.glDrawLine(0, 20, Main.screenSize[0]-1, 20);
|
|
||||||
renderer.glColor3i(0, 0, 0);
|
|
||||||
if (Keyboard.shift) {
|
|
||||||
drawSkinPart(2 + 18 * 0, 2, 16 * 2, 16 * 0, 16 + 16 * 2, 16 + 16 * 0);
|
|
||||||
} else {
|
|
||||||
drawSkinPart(2 + 18 * 0, 2, 16 * 3, 16 * 0, 16 + 16 * 3, 16 + 16 * 0);
|
|
||||||
}
|
|
||||||
if (Keyboard.alpha) {
|
|
||||||
drawSkinPart(2 + 18 * 1, 2, 16 * 0, 16 * 0, 16 + 16 * 0, 16 + 16 * 0);
|
|
||||||
} else {
|
|
||||||
drawSkinPart(2 + 18 * 1, 2, 16 * 1, 16 * 0, 16 + 16 * 1, 16 + 16 * 0);
|
|
||||||
}
|
|
||||||
/*
|
|
||||||
if (Calculator.angleMode == AngleMode.DEG) {
|
|
||||||
drawSkinPart(8 + 18 * 2, 2, 16 * 4, 16 * 0, 16 + 16 * 4, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 3, 2, 16 * 7, 16 * 0, 16 + 16 * 7, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 4, 2, 16 * 9, 16 * 0, 16 + 16 * 9, 16 + 16 * 0);
|
|
||||||
} else if (Calculator.angleMode == AngleMode.RAD) {
|
|
||||||
drawSkinPart(8 + 18 * 2, 2, 16 * 5, 16 * 0, 16 + 16 * 5, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 3, 2, 16 * 6, 16 * 0, 16 + 16 * 6, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 4, 2, 16 * 9, 16 * 0, 16 + 16 * 9, 16 + 16 * 0);
|
|
||||||
} else if (Calculator.angleMode == AngleMode.GRA) {
|
|
||||||
drawSkinPart(8 + 18 * 2, 2, 16 * 5, 16 * 0, 16 + 16 * 5, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 3, 2, 16 * 7, 16 * 0, 16 + 16 * 7, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 4, 2, 16 * 8, 16 * 0, 16 + 16 * 8, 16 + 16 * 0);
|
|
||||||
} else {
|
|
||||||
drawSkinPart(8 + 18 * 2, 2, 16 * 5, 16 * 0, 16 + 16 * 5, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 3, 2, 16 * 7, 16 * 0, 16 + 16 * 7, 16 + 16 * 0);
|
|
||||||
drawSkinPart(8 + 18 * 4, 2, 16 * 9, 16 * 0, 16 + 16 * 9, 16 + 16 * 0);
|
|
||||||
}*/
|
|
||||||
|
|
||||||
int padding = 2;
|
|
||||||
|
|
||||||
int brightness = (int) (Math.ceil(PIDisplay.brightness * 9));
|
|
||||||
if (brightness <= 10) {
|
|
||||||
drawSkinPart(Main.screenSize[0] - (padding + 16), 2, 16 * brightness, 16 * 1, 16 + 16 * brightness, 16 + 16 * 1);
|
|
||||||
} else {
|
|
||||||
Utils.debug.println("Brightness error");
|
|
||||||
}
|
|
||||||
|
|
||||||
padding += 18 + 6;
|
|
||||||
|
|
||||||
boolean canGoBack = canGoBack();
|
|
||||||
boolean canGoForward = canGoForward();
|
|
||||||
|
|
||||||
if (Main.haxMode) {
|
|
||||||
drawSkinPart(Main.screenSize[0] - (padding + 16), 2, 16 * 18, 16 * 0, 16 + 16 * 18, 16 + 16 * 0);
|
|
||||||
padding += 18 + 6;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (canGoBack && canGoForward) {
|
|
||||||
drawSkinPart(Main.screenSize[0] - (padding + 16), 2, 16 * 14, 16 * 0, 16 + 16 * 14, 16 + 16 * 0);
|
|
||||||
} else if (canGoBack) {
|
|
||||||
drawSkinPart(Main.screenSize[0] - (padding + 16), 2, 16 * 15, 16 * 0, 16 + 16 * 15, 16 + 16 * 0);
|
|
||||||
} else if (canGoForward) {
|
|
||||||
drawSkinPart(Main.screenSize[0] - (padding + 16), 2, 16 * 16, 16 * 0, 16 + 16 * 16, 16 + 16 * 0);
|
|
||||||
} else {
|
|
||||||
drawSkinPart(Main.screenSize[0] - (padding + 16), 2, 16 * 17, 16 * 0, 16 + 16 * 17, 16 + 16 * 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
padding += 18;
|
|
||||||
|
|
||||||
screen.renderStatusbar();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void draw_screen() {
|
|
||||||
screen.render();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void draw_bottom() {
|
|
||||||
renderer.glDrawStringLeft(2, 90, displayDebugString);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void draw_world() {
|
|
||||||
renderer.glColor3i(255, 255, 255);
|
|
||||||
|
|
||||||
if (error != null) {
|
|
||||||
renderer.glSetFont(Utils.getFont(false, false));
|
|
||||||
renderer.glColor3i(129, 28, 22);
|
|
||||||
renderer.glDrawStringRight(Main.screenSize[0] - 2, Main.screenSize[1]- PIDisplay.glyphsHeight[1] - 2, "ANDREA CAVALLI'S CALCULATOR");
|
|
||||||
renderer.glColor3i(149, 32, 26);
|
|
||||||
renderer.glDrawStringCenter((Main.screenSize[0] / 2), 22, error);
|
|
||||||
renderer.glColor3i(164, 34, 28);
|
|
||||||
int i = 22;
|
|
||||||
for (String stackPart : errorStackTrace) {
|
|
||||||
renderer.glDrawStringLeft(2, 22 + i, stackPart);
|
|
||||||
i += 11;
|
|
||||||
}
|
|
||||||
renderer.glSetFont(fonts[0]);
|
|
||||||
renderer.glColor3i(129, 28, 22);
|
|
||||||
renderer.glDrawStringCenter((Main.screenSize[0] / 2), 11, "UNEXPECTED EXCEPTION");
|
|
||||||
} else {
|
|
||||||
draw_screen();
|
|
||||||
draw_status();
|
|
||||||
draw_bottom();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void draw() {
|
|
||||||
draw_init();
|
|
||||||
draw_world();
|
|
||||||
}
|
|
||||||
|
|
||||||
private long precTime = -1;
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void refresh() {
|
|
||||||
float dt = 0;
|
|
||||||
long newtime = System.nanoTime();
|
|
||||||
if (precTime == -1) {
|
|
||||||
dt = 0;
|
|
||||||
} else {
|
|
||||||
dt = (float) ((newtime - precTime) / 1000000000d);
|
|
||||||
}
|
|
||||||
precTime = newtime;
|
|
||||||
/*
|
|
||||||
* Calcoli
|
|
||||||
*/
|
|
||||||
checkDisplayResized();
|
|
||||||
|
|
||||||
screen.beforeRender(dt);
|
|
||||||
|
|
||||||
if(dt >= 0.03 || screen.mustBeRefreshed()) {
|
|
||||||
draw();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private void checkDisplayResized() {
|
|
||||||
if (display.wasResized()) {
|
|
||||||
Main.screenSize[0] = display.getWidth();
|
|
||||||
Main.screenSize[1]= display.getHeight();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
public void loop() {
|
|
||||||
try {
|
|
||||||
load_skin();
|
|
||||||
load_fonts();
|
|
||||||
display.create();
|
|
||||||
|
|
||||||
try {
|
|
||||||
screen.initialize();
|
|
||||||
} catch (Exception e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
System.exit(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
display.start(this);
|
|
||||||
|
|
||||||
Main.instance.afterStart();
|
|
||||||
|
|
||||||
double extratime = 0;
|
|
||||||
while (CPUDisplay.initialized) {
|
|
||||||
long start = System.currentTimeMillis();
|
|
||||||
display.repaint();
|
|
||||||
long end = System.currentTimeMillis();
|
|
||||||
double delta = (end - start) / 1000d;
|
|
||||||
int deltaInt = (int) Math.floor(delta);
|
|
||||||
int extraTimeInt = (int) Math.floor(extratime);
|
|
||||||
if (extraTimeInt + deltaInt < 50) {
|
|
||||||
Thread.sleep(50 - (extraTimeInt + deltaInt));
|
|
||||||
extratime = 0;
|
|
||||||
} else {
|
|
||||||
extratime += delta - 50d;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} catch (Exception ex) {
|
|
||||||
ex.printStackTrace();
|
|
||||||
} finally {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void changeBrightness(float change) {
|
|
||||||
setBrightness(brightness + change);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void setBrightness(float newval) {
|
|
||||||
if (newval >= 0 && newval <= 1) {
|
|
||||||
brightness = newval;
|
|
||||||
if (Utils.debugOn == false) {
|
|
||||||
Gpio.pwmWrite(12, (int) Math.ceil(brightness*1024));
|
|
||||||
// SoftPwm.softPwmWrite(12, (int)(Math.ceil(brightness*10)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void cycleBrightness(boolean reverse) {
|
|
||||||
final float step = reverse?-0.1f:0.1f;
|
|
||||||
if (brightness + step > 1f) {
|
|
||||||
setBrightness(0f);
|
|
||||||
} else if (brightness + step <= 0f) {
|
|
||||||
setBrightness(1.0f);
|
|
||||||
} else {
|
|
||||||
changeBrightness(step);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static float getBrightness() {
|
|
||||||
return brightness;
|
|
||||||
}
|
|
||||||
|
|
||||||
public float[] colore = new float[] { 0.0f, 0.0f, 0.0f, 1.0f };
|
|
||||||
public static int currentSession = 0;
|
|
||||||
public static Screen[] sessions = new Screen[5];
|
|
||||||
|
|
||||||
public static void colore(float f1, float f2, float f3, float f4) {
|
|
||||||
PIDisplay.INSTANCE.colore = new float[] { f1, f2, f3, f4 };
|
|
||||||
renderer.glColor4i((int) (f1 * 255), (int) (f2 * 255), (int) (f3 * 255), (int) (f4 * 255));
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Drawable getDrawable() {
|
|
||||||
return INSTANCE;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,6 +1,6 @@
|
|||||||
package org.warp.picalculator.gui.graphicengine;
|
package org.warp.picalculator.gui.graphicengine;
|
||||||
|
|
||||||
import java.awt.image.BufferedImage;
|
import java.io.IOException;
|
||||||
|
|
||||||
public interface Display {
|
public interface Display {
|
||||||
|
|
||||||
@ -29,4 +29,12 @@ public interface Display {
|
|||||||
public void repaint();
|
public void repaint();
|
||||||
|
|
||||||
public Renderer getRenderer();
|
public Renderer getRenderer();
|
||||||
|
|
||||||
|
public RAWFont loadFont(String file) throws IOException;
|
||||||
|
|
||||||
|
public RAWSkin loadSkin(String file) throws IOException;
|
||||||
|
|
||||||
|
public void waitUntilExit();
|
||||||
|
|
||||||
|
public boolean isSupported();
|
||||||
}
|
}
|
||||||
|
@ -1,182 +1,14 @@
|
|||||||
package org.warp.picalculator.gui.graphicengine;
|
package org.warp.picalculator.gui.graphicengine;
|
||||||
|
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
import java.awt.image.DataBufferInt;
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.lang.ref.WeakReference;
|
|
||||||
import java.net.URL;
|
|
||||||
import java.util.logging.Level;
|
|
||||||
import java.util.logging.Logger;
|
|
||||||
|
|
||||||
import javax.imageio.ImageIO;
|
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
|
||||||
import org.warp.picalculator.Utils;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @author andreacv
|
* @author andreacv
|
||||||
*/
|
*/
|
||||||
public class RAWFont {
|
public interface RAWFont extends RAWSkin {
|
||||||
|
|
||||||
public boolean[][] rawchars;
|
public int getStringWidth(String text);
|
||||||
public int[] chars32;
|
|
||||||
public int minBound = 10;
|
|
||||||
public int maxBound = 0;
|
|
||||||
public int charW;
|
|
||||||
public int charH;
|
|
||||||
public int charS;
|
|
||||||
public int charIntCount;
|
|
||||||
public boolean installed;
|
|
||||||
public static final int intBits = 31;
|
|
||||||
|
|
||||||
public void create(String name) {
|
public int getCharacterWidth();
|
||||||
try {
|
|
||||||
loadFont("/font_"+name+".rft");
|
|
||||||
} catch (IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
System.exit(1);
|
|
||||||
}
|
|
||||||
chars32 = new int[(maxBound-minBound)*charIntCount];
|
|
||||||
for (int charIndex = 0; charIndex < maxBound-minBound; charIndex++) {
|
|
||||||
boolean[] currentChar = rawchars[charIndex];
|
|
||||||
if (currentChar == null) {
|
|
||||||
int currentInt = 0;
|
|
||||||
int currentBit = 0;
|
|
||||||
for (int i = 0; i < charS; i++) {
|
|
||||||
if (currentInt*intBits+currentBit >= (currentInt+1)*intBits) {
|
|
||||||
currentInt += 1;
|
|
||||||
currentBit = 0;
|
|
||||||
}
|
|
||||||
chars32[charIndex*charIntCount+currentInt] = (chars32[charIndex*charIntCount+currentInt] << 1) + 1;
|
|
||||||
currentBit += 1;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
int currentInt = 0;
|
|
||||||
int currentBit = 0;
|
|
||||||
for (int i = 0; i < charS; i++) {
|
|
||||||
if (currentBit >= intBits) {
|
|
||||||
currentInt += 1;
|
|
||||||
currentBit = 0;
|
|
||||||
}
|
|
||||||
chars32[charIndex*charIntCount+currentInt] = (chars32[charIndex*charIntCount+currentInt]) | ((currentChar[i] ? 1 : 0) << currentBit);
|
|
||||||
currentBit++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Object obj = new Object();
|
public int getCharacterHeight();
|
||||||
WeakReference<Object> ref = new WeakReference<>(obj);
|
|
||||||
obj = null;
|
|
||||||
while (ref.get() != null) {
|
|
||||||
System.gc();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void loadFont(String string) throws IOException {
|
|
||||||
URL res = Main.instance.getClass().getResource(string);
|
|
||||||
int[] file = Utils.realBytes(Utils.convertStreamToByteArray(res.openStream(), res.getFile().length()));
|
|
||||||
int filelength = file.length;
|
|
||||||
if (filelength >= 16) {
|
|
||||||
if (file[0x0] == 114 && file[0x1] == 97 && file[0x2] == 119 && file[0x3] == 0xFF && file[0x8] == 0xFF && file[0xD] == 0xFF) {
|
|
||||||
charW = file[0x4] << 8 | file[0x5];
|
|
||||||
charH = file[0x6] << 8 | file[0x7];
|
|
||||||
charS = charW*charH;
|
|
||||||
charIntCount = (int) Math.ceil(((double)charS)/((double)intBits));
|
|
||||||
minBound = file[0x9] << 24 | file[0xA] << 16 | file[0xB] << 8 | file[0xC];
|
|
||||||
maxBound = file[0xE] << 24 | file[0xF] << 16 | file[0x10] << 8 | file[0x11];
|
|
||||||
if (maxBound <= minBound) {
|
|
||||||
maxBound = 10000; //TODO remove it: temp fix
|
|
||||||
}
|
|
||||||
rawchars = new boolean[maxBound-minBound][];
|
|
||||||
int index = 0x12;
|
|
||||||
while (index < filelength) {
|
|
||||||
try {
|
|
||||||
int charIndex = file[index] << 8 | file[index+1];
|
|
||||||
boolean[] rawchar = new boolean[charS];
|
|
||||||
int charbytescount = 0;
|
|
||||||
while (charbytescount*8 < charS) {
|
|
||||||
charbytescount+=1;
|
|
||||||
}
|
|
||||||
int currentBit = 0;
|
|
||||||
for (int i = 0; i <= charbytescount; i++) {
|
|
||||||
for (int bit = 0; bit < 8; bit++) {
|
|
||||||
if (currentBit >= charS) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
rawchar[currentBit] = (((file[index + 2 + i] >> (8-1-bit)) & 0x1)==1)?true:false;
|
|
||||||
currentBit++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
rawchars[charIndex - minBound] = rawchar;
|
|
||||||
index += 2 + charbytescount;
|
|
||||||
}
|
|
||||||
catch (Exception ex) {
|
|
||||||
ex.printStackTrace();
|
|
||||||
System.out.println(string);
|
|
||||||
System.exit(-1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
throw new IOException();
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
throw new IOException();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int[] getCharIndexes(String txt) {
|
|
||||||
final int l = txt.length();
|
|
||||||
int[] indexes = new int[l];
|
|
||||||
char[] chars = txt.toCharArray();
|
|
||||||
for (int i = 0; i < l; i++) {
|
|
||||||
indexes[i] = (chars[i] & 0xFFFF)-minBound;
|
|
||||||
}
|
|
||||||
return indexes;
|
|
||||||
}
|
|
||||||
|
|
||||||
@SuppressWarnings("unused")
|
|
||||||
private void saveArray(int[] screen, String coutputpng) {
|
|
||||||
BufferedImage bi = new BufferedImage(300, 200, BufferedImage.TYPE_INT_RGB);
|
|
||||||
final int[] a = ((DataBufferInt) bi.getRaster().getDataBuffer()).getData();
|
|
||||||
System.arraycopy(screen, 0, a, 0, screen.length);
|
|
||||||
try {
|
|
||||||
ImageIO.write(bi, "PNG", new File(coutputpng));
|
|
||||||
} catch (IOException ex) {
|
|
||||||
Logger.getLogger(RAWFont.class.getName()).log(Level.SEVERE, null, ex);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void drawText(int[] screen, int[] screenSize, int x, int y, int[] text, int color) {
|
|
||||||
final int screenLength = screen.length;
|
|
||||||
int screenPos = 0;
|
|
||||||
|
|
||||||
|
|
||||||
int currentInt;
|
|
||||||
int currentIntBitPosition;
|
|
||||||
int bitData;
|
|
||||||
int cpos;
|
|
||||||
int j;
|
|
||||||
final int l = text.length;
|
|
||||||
for (int i = 0; i < l; i++) {
|
|
||||||
cpos = (i * (charW + 1));
|
|
||||||
final int charIndex = text[i];
|
|
||||||
for (int dy = 0; dy < charH; dy++) {
|
|
||||||
for (int dx = 0; dx < charW; dx++) {
|
|
||||||
j = x + cpos + dx;
|
|
||||||
if (j > 0 & j < screenSize[0]) {
|
|
||||||
int bit = dx + dy * charW;
|
|
||||||
currentInt = (int) (Math.floor(bit)/(intBits));
|
|
||||||
currentIntBitPosition = bit-(currentInt*intBits);
|
|
||||||
bitData = (chars32[charIndex*charIntCount+currentInt] >> currentIntBitPosition) & 1;
|
|
||||||
screenPos = x + cpos + dx + (y + dy) * screenSize[0];
|
|
||||||
if (bitData == 1 & screenLength > screenPos) {
|
|
||||||
screen[screenPos] = color;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
12
src/org/warp/picalculator/gui/graphicengine/RAWSkin.java
Normal file
12
src/org/warp/picalculator/gui/graphicengine/RAWSkin.java
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
package org.warp.picalculator.gui.graphicengine;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
public interface RAWSkin {
|
||||||
|
|
||||||
|
public void load(String file) throws IOException;
|
||||||
|
|
||||||
|
public void initialize(Display d);
|
||||||
|
|
||||||
|
public void use(Display d);
|
||||||
|
}
|
@ -1,31 +1,33 @@
|
|||||||
package org.warp.picalculator.gui.graphicengine;
|
package org.warp.picalculator.gui.graphicengine;
|
||||||
|
|
||||||
import java.awt.FontMetrics;
|
import java.awt.FontMetrics;
|
||||||
import java.awt.image.BufferedImage;
|
|
||||||
|
|
||||||
public interface Renderer {
|
public interface Renderer {
|
||||||
public void glColor3i(int r, int gg, int b);
|
public void glColor3i(int r, int gg, int b);
|
||||||
|
|
||||||
public void glColor(int c);
|
public void glColor(int c);
|
||||||
|
|
||||||
|
public void glColor4i(int red, int green, int blue, int alpha);
|
||||||
|
|
||||||
|
public void glColor3f(float red, float green, float blue);
|
||||||
|
|
||||||
|
public void glColor4f(float red, float green, float blue, float alpha);
|
||||||
|
|
||||||
|
public void glClearColor4i(int red, int green, int blue, int alpha);
|
||||||
|
|
||||||
|
public void glClearColor4f(float red, float green, float blue, float alpha);
|
||||||
|
|
||||||
public int glGetClearColor();
|
public int glGetClearColor();
|
||||||
|
|
||||||
public void glClearColor(int c);
|
public void glClearColor(int c);
|
||||||
|
|
||||||
public void glColor4i(int red, int green, int blue, int alpha);
|
public void glClear(int screenWidth, int screenHeight);
|
||||||
|
|
||||||
public void glClearColor(int red, int green, int blue, int alpha);
|
|
||||||
|
|
||||||
public void glClear();
|
|
||||||
|
|
||||||
public void glDrawSkin(int skinwidth, int[] skin, int x0, int y0, int s0, int t0, int s1, int t1, boolean transparent);
|
|
||||||
|
|
||||||
public void glDrawLine(int x0, int y0, int x1, int y1);
|
public void glDrawLine(int x0, int y0, int x1, int y1);
|
||||||
|
|
||||||
public void glFillRect(int x0, int y0, int w1, int h1);
|
public void glFillRect(int x, int y, int width, int height, float uvX, float uvY, float uvWidth, float uvHeight);
|
||||||
|
|
||||||
@Deprecated
|
public void glFillColor(int x, int y, int width, int height);
|
||||||
public int[] getMatrixOfImage(BufferedImage bufferedImage);
|
|
||||||
|
|
||||||
public void glDrawStringLeft(int x, int y, String text);
|
public void glDrawStringLeft(int x, int y, String text);
|
||||||
|
|
||||||
@ -33,11 +35,7 @@ public interface Renderer {
|
|||||||
|
|
||||||
public void glDrawStringRight(int x, int y, String text);
|
public void glDrawStringRight(int x, int y, String text);
|
||||||
|
|
||||||
public void glSetFont(RAWFont font);
|
public void glClearSkin();
|
||||||
|
|
||||||
public int glGetStringWidth(RAWFont rf, String text);
|
|
||||||
|
|
||||||
public int glGetFontWidth(FontMetrics fm, String text);
|
|
||||||
|
|
||||||
public RAWFont getCurrentFont();
|
public RAWFont getCurrentFont();
|
||||||
}
|
}
|
@ -1,35 +1,43 @@
|
|||||||
package org.warp.picalculator.gui.graphicengine.cpu;
|
package org.warp.picalculator.gui.graphicengine.cpu;
|
||||||
|
|
||||||
import java.awt.FontMetrics;
|
import java.awt.FontMetrics;
|
||||||
|
import java.awt.GraphicsEnvironment;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.Display;
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
import org.warp.picalculator.gui.graphicengine.Drawable;
|
import org.warp.picalculator.gui.graphicengine.Drawable;
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
import org.warp.picalculator.gui.graphicengine.Renderer;
|
import org.warp.picalculator.gui.graphicengine.Renderer;
|
||||||
|
|
||||||
public class CPUDisplay implements Display {
|
public class CPUDisplay implements Display {
|
||||||
|
|
||||||
private static SwingWindow INSTANCE;
|
private SwingWindow INSTANCE;
|
||||||
public static int[] size = new int[] { 1, 1 };
|
public int[] size = new int[] { 1, 1 };
|
||||||
public static BufferedImage g = new BufferedImage(size[0], size[1], BufferedImage.TYPE_INT_RGB);
|
public BufferedImage g = new BufferedImage(size[0], size[1], BufferedImage.TYPE_INT_RGB);
|
||||||
static int[] canvas2d = new int[1];
|
static int[] canvas2d = new int[1];
|
||||||
public static int color = 0xFF000000;
|
public int color = 0xFF000000;
|
||||||
public static boolean initialized = false;
|
public volatile boolean initialized = false;
|
||||||
|
private final CPURenderer r = new CPURenderer();
|
||||||
|
|
||||||
|
@Override
|
||||||
public void setTitle(String title) {
|
public void setTitle(String title) {
|
||||||
INSTANCE.setTitle(title);
|
INSTANCE.setTitle(title);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void setResizable(boolean r) {
|
public void setResizable(boolean r) {
|
||||||
INSTANCE.setResizable(r);
|
INSTANCE.setResizable(r);
|
||||||
if (!r)
|
if (!r) {
|
||||||
INSTANCE.setUndecorated(true);
|
INSTANCE.setUndecorated(true);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void setDisplayMode(final int ww, final int wh) {
|
public void setDisplayMode(final int ww, final int wh) {
|
||||||
INSTANCE.setSize(ww, wh);
|
INSTANCE.setSize(ww, wh);
|
||||||
size = new int[] { ww, wh };
|
size = new int[] { ww, wh };
|
||||||
@ -38,14 +46,16 @@ public class CPUDisplay implements Display {
|
|||||||
INSTANCE.wasResized = false;
|
INSTANCE.wasResized = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void create() {
|
public void create() {
|
||||||
INSTANCE = new SwingWindow(PIDisplay.getDrawable());
|
INSTANCE = new SwingWindow(this, DisplayManager.getDrawable());
|
||||||
setResizable(Utils.debugOn&!Utils.debugThirdScreen);
|
setResizable(Utils.debugOn & !Utils.debugThirdScreen);
|
||||||
setDisplayMode(Main.screenSize[0], Main.screenSize[1]);
|
setDisplayMode(Main.screenSize[0], Main.screenSize[1]);
|
||||||
INSTANCE.setVisible(true);
|
INSTANCE.setVisible(true);
|
||||||
initialized = true;
|
initialized = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public boolean wasResized() {
|
public boolean wasResized() {
|
||||||
if (INSTANCE.wasResized) {
|
if (INSTANCE.wasResized) {
|
||||||
size = new int[] { INSTANCE.getWidth(), INSTANCE.getHeight() };
|
size = new int[] { INSTANCE.getWidth(), INSTANCE.getHeight() };
|
||||||
@ -57,37 +67,66 @@ public class CPUDisplay implements Display {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public int getWidth() {
|
public int getWidth() {
|
||||||
return INSTANCE.getWidth()-Main.screenPos[0];
|
return INSTANCE.getWidth() - Main.screenPos[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public int getHeight() {
|
public int getHeight() {
|
||||||
return INSTANCE.getHeight()-Main.screenPos[1];
|
return INSTANCE.getHeight() - Main.screenPos[1];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void destroy() {
|
public void destroy() {
|
||||||
initialized = false;
|
initialized = false;
|
||||||
INSTANCE.setVisible(false);
|
INSTANCE.setVisible(false);
|
||||||
INSTANCE.dispose();
|
INSTANCE.dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void start(Drawable d) {
|
public void start(Drawable d) {
|
||||||
|
Thread th = new Thread(() -> {
|
||||||
|
try {
|
||||||
|
double extratime = 0;
|
||||||
|
while (initialized) {
|
||||||
|
final long start = System.currentTimeMillis();
|
||||||
|
repaint();
|
||||||
|
final long end = System.currentTimeMillis();
|
||||||
|
final double delta = (end - start) / 1000d;
|
||||||
|
final int deltaInt = (int) Math.floor(delta);
|
||||||
|
final int extraTimeInt = (int) Math.floor(extratime);
|
||||||
|
if (extraTimeInt + deltaInt < 50) {
|
||||||
|
Thread.sleep(50 - (extraTimeInt + deltaInt));
|
||||||
|
extratime = 0;
|
||||||
|
} else {
|
||||||
|
extratime += delta - 50d;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (final InterruptedException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
th.setName("Game loop thread");
|
||||||
|
th.setDaemon(true);
|
||||||
|
th.start();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Deprecated()
|
@Deprecated()
|
||||||
public void refresh() {
|
public void refresh() {
|
||||||
if (PIDisplay.screen == null || (PIDisplay.error != null && PIDisplay.error.length() > 0) || PIDisplay.screen == null || PIDisplay.screen.mustBeRefreshed()) {
|
if (DisplayManager.screen == null || (DisplayManager.error != null && DisplayManager.error.length() > 0) || DisplayManager.screen == null || DisplayManager.screen.mustBeRefreshed()) {
|
||||||
CPUDisplay.INSTANCE.c.repaint();
|
INSTANCE.c.repaint();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void repaint() {
|
public void repaint() {
|
||||||
CPUDisplay.INSTANCE.c.repaint();
|
INSTANCE.c.repaint();
|
||||||
}
|
}
|
||||||
|
|
||||||
public abstract class Startable {
|
public abstract class Startable {
|
||||||
public Startable() {
|
public Startable() {
|
||||||
this.force = false;
|
force = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Startable(boolean force) {
|
public Startable(boolean force) {
|
||||||
@ -99,58 +138,70 @@ public class CPUDisplay implements Display {
|
|||||||
public abstract void run();
|
public abstract void run();
|
||||||
}
|
}
|
||||||
|
|
||||||
public class Render implements Renderer {
|
public class CPURenderer implements Renderer {
|
||||||
public int clearcolor = 0xFFc5c2af;
|
public int clearcolor = 0xFFc5c2af;
|
||||||
public RAWFont currentFont;
|
public CPUFont currentFont;
|
||||||
|
public CPUSkin currentSkin;
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glColor3i(int r, int gg, int b) {
|
public void glColor3i(int r, int gg, int b) {
|
||||||
glColor4i(r, gg, b, 255);
|
glColor4i(r, gg, b, 255);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glColor(int c) {
|
public void glColor(int c) {
|
||||||
color = c & 0xFFFFFFFF;
|
color = c & 0xFFFFFFFF;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glClearColor(int c) {
|
public void glClearColor(int c) {
|
||||||
clearcolor = c & 0xFFFFFFFF;
|
clearcolor = c & 0xFFFFFFFF;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glColor4i(int red, int green, int blue, int alpha) {
|
public void glColor4i(int red, int green, int blue, int alpha) {
|
||||||
color = (alpha << 24) + (red << 16) + (green << 8) + (blue);
|
color = (alpha << 24) + (red << 16) + (green << 8) + (blue);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void glClearColor(int red, int green, int blue, int alpha) {
|
@Override
|
||||||
|
public void glClearColor4i(int red, int green, int blue, int alpha) {
|
||||||
clearcolor = (alpha << 24) + (red << 16) + (green << 8) + (blue);
|
clearcolor = (alpha << 24) + (red << 16) + (green << 8) + (blue);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void glClear() {
|
@Override
|
||||||
for (int x = 0; x < size[0]; x++) {
|
public void glClearColor4f(float red, float green, float blue, float alpha) {
|
||||||
for (int y = 0; y < size[1]; y++) {
|
clearcolor = ((int)(alpha*255) << 24) + ((int)(red*255) << 16) + ((int)(green*255) << 8) + ((int)(blue*255));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glClear(int screenWidth, int screenHeight) {
|
||||||
|
for (int x = 0; x < screenWidth; x++) {
|
||||||
|
for (int y = 0; y < screenHeight; y++) {
|
||||||
canvas2d[x + y * size[0]] = clearcolor;
|
canvas2d[x + y * size[0]] = clearcolor;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void glDrawSkin(int skinwidth, int[] skin, int x0, int y0, int s0, int t0, int s1, int t1, boolean transparent) {
|
private void glDrawSkin(int x0, int y0, int s0, int t0, int s1, int t1, boolean transparent) {
|
||||||
x0+=Main.screenPos[0];
|
x0 += Main.screenPos[0];
|
||||||
y0+=Main.screenPos[1];
|
y0 += Main.screenPos[1];
|
||||||
int oldColor;
|
int oldColor;
|
||||||
int newColor;
|
int newColor;
|
||||||
int onex = s0 <= s1?1:-1;
|
final int onex = s0 <= s1 ? 1 : -1;
|
||||||
int oney = t0 <= t1?1:-1;
|
final int oney = t0 <= t1 ? 1 : -1;
|
||||||
int width = 0;
|
int width = 0;
|
||||||
int height = 0;
|
int height = 0;
|
||||||
if (onex == -1) {
|
if (onex == -1) {
|
||||||
int s00 = s0;
|
final int s00 = s0;
|
||||||
s0 = s1;
|
s0 = s1;
|
||||||
s1 = s00;
|
s1 = s00;
|
||||||
width = s1-s0;
|
width = s1 - s0;
|
||||||
}
|
}
|
||||||
if (oney == -1) {
|
if (oney == -1) {
|
||||||
int t00 = t0;
|
final int t00 = t0;
|
||||||
t0 = t1;
|
t0 = t1;
|
||||||
t1 = t00;
|
t1 = t00;
|
||||||
height = t1-t0;
|
height = t1 - t0;
|
||||||
}
|
}
|
||||||
if (x0 >= size[0] || y0 >= size[0]) {
|
if (x0 >= size[0] || y0 >= size[0]) {
|
||||||
return;
|
return;
|
||||||
@ -179,28 +230,35 @@ public class CPUDisplay implements Display {
|
|||||||
}
|
}
|
||||||
y0 = 0;
|
y0 = 0;
|
||||||
}
|
}
|
||||||
|
int pixelX;
|
||||||
|
int pixelY;
|
||||||
for (int texx = 0; texx < s1 - s0; texx++) {
|
for (int texx = 0; texx < s1 - s0; texx++) {
|
||||||
for (int texy = 0; texy < t1 - t0; texy++) {
|
for (int texy = 0; texy < t1 - t0; texy++) {
|
||||||
newColor = skin[(s0 + texx) + (t0 + texy) * skinwidth];
|
pixelX = (x0 + texx * onex + width);
|
||||||
if (transparent) {
|
pixelY = (y0 + texy * oney + height);
|
||||||
oldColor = canvas2d[(x0 + texx*onex + width) + (y0 + texy*oney + height) * size[0]];
|
if (pixelX - (pixelX % size[0]) == 0) {
|
||||||
float a2 = (newColor >> 24 & 0xFF) / 255f;
|
newColor = currentSkin.skinData[(s0 + texx) + (t0 + texy) * currentSkin.skinSize[0]];
|
||||||
float a1 = 1f-a2;
|
if (transparent) {
|
||||||
int r = (int) ((oldColor >> 16 & 0xFF) * a1 + (newColor >> 16 & 0xFF) * a2);
|
oldColor = canvas2d[pixelX + pixelY * size[0]];
|
||||||
int g = (int) ((oldColor >> 8 & 0xFF) * a1 + (newColor >> 8 & 0xFF) * a2);
|
final float a2 = (newColor >> 24 & 0xFF) / 255f;
|
||||||
int b = (int) ((oldColor & 0xFF) * a1 + (newColor & 0xFF) * a2);
|
final float a1 = 1f - a2;
|
||||||
newColor = 0xFF000000 | r << 16 | g << 8 | b;
|
final int r = (int) ((oldColor >> 16 & 0xFF) * a1 + (newColor >> 16 & 0xFF) * a2);
|
||||||
|
final int g = (int) ((oldColor >> 8 & 0xFF) * a1 + (newColor >> 8 & 0xFF) * a2);
|
||||||
|
final int b = (int) ((oldColor & 0xFF) * a1 + (newColor & 0xFF) * a2);
|
||||||
|
newColor = 0xFF000000 | r << 16 | g << 8 | b;
|
||||||
|
}
|
||||||
|
canvas2d[pixelX + pixelY * size[0]] = newColor;
|
||||||
}
|
}
|
||||||
canvas2d[(x0 + texx*onex + width) + (y0 + texy*oney + height) * size[0]] = newColor;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glDrawLine(int x0, int y0, int x1, int y1) {
|
public void glDrawLine(int x0, int y0, int x1, int y1) {
|
||||||
x0+=Main.screenPos[0];
|
x0 += Main.screenPos[0];
|
||||||
x1+=Main.screenPos[0];
|
x1 += Main.screenPos[0];
|
||||||
y0+=Main.screenPos[1];
|
y0 += Main.screenPos[1];
|
||||||
y1+=Main.screenPos[1];
|
y1 += Main.screenPos[1];
|
||||||
if (x0 >= size[0] || y0 >= size[0]) {
|
if (x0 >= size[0] || y0 >= size[0]) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -213,7 +271,7 @@ public class CPUDisplay implements Display {
|
|||||||
canvas2d[x0 + (y0 + y) * size[0]] = color;
|
canvas2d[x0 + (y0 + y) * size[0]] = color;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
int m = (y1 - y0) / (x1 - x0);
|
final int m = (y1 - y0) / (x1 - x0);
|
||||||
for (int texx = 0; texx <= x1 - x0; texx++) {
|
for (int texx = 0; texx <= x1 - x0; texx++) {
|
||||||
if (x0 + texx < size[0] && y0 + (m * texx) < size[1]) {
|
if (x0 + texx < size[0] && y0 + (m * texx) < size[1]) {
|
||||||
canvas2d[(x0 + texx) + (y0 + (m * texx)) * size[0]] = color;
|
canvas2d[(x0 + texx) + (y0 + (m * texx)) * size[0]] = color;
|
||||||
@ -222,12 +280,23 @@ public class CPUDisplay implements Display {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void glFillRect(int x0, int y0, int w1, int h1) {
|
@Override
|
||||||
x0+=Main.screenPos[0];
|
public void glFillRect(int x, int y, int width, int height, float uvX, float uvY, float uvWidth,
|
||||||
y0+=Main.screenPos[1];
|
float uvHeight) {
|
||||||
int x1 = x0+w1;
|
if (currentSkin != null) {
|
||||||
int y1 = y0+h1;
|
glDrawSkin(x, y, (int) uvX, (int) uvY, (int) (uvWidth + uvX), (int) (uvHeight + uvY), true);
|
||||||
if (x0 >= size[0] || y0 >= size[0]) {
|
} else {
|
||||||
|
glFillColor(x, y, width, height);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glFillColor(int x, int y, int width, int height) {
|
||||||
|
x += Main.screenPos[0];
|
||||||
|
y += Main.screenPos[1];
|
||||||
|
int x1 = x + width;
|
||||||
|
int y1 = y + height;
|
||||||
|
if (x >= size[0] || y >= size[0]) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (x1 >= size[0]) {
|
if (x1 >= size[0]) {
|
||||||
@ -237,57 +306,62 @@ public class CPUDisplay implements Display {
|
|||||||
y1 = size[1];
|
y1 = size[1];
|
||||||
}
|
}
|
||||||
final int sizeW = size[0];
|
final int sizeW = size[0];
|
||||||
for (int x = x0; x < x1; x++) {
|
for (int px = x; px < x1; px++) {
|
||||||
for (int y = y0; y < y1; y++) {
|
for (int py = y; py < y1; py++) {
|
||||||
canvas2d[(x) + (y) * sizeW] = color;
|
canvas2d[(px) + (py) * sizeW] = color;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public int[] getMatrixOfImage(BufferedImage bufferedImage) {
|
@Override
|
||||||
int width = bufferedImage.getWidth(null);
|
public void glDrawStringLeft(int x, int y, String textString) {
|
||||||
int height = bufferedImage.getHeight(null);
|
x += Main.screenPos[0];
|
||||||
int[] pixels = new int[width * height];
|
y += Main.screenPos[1];
|
||||||
for (int i = 0; i < width; i++) {
|
|
||||||
for (int j = 0; j < height; j++) {
|
final int[] text = currentFont.getCharIndexes(textString);
|
||||||
pixels[i + j * width] = bufferedImage.getRGB(i, j);
|
final int[] screen = canvas2d;
|
||||||
|
final int[] screenSize = size;
|
||||||
|
final int screenLength = screen.length;
|
||||||
|
int screenPos = 0;
|
||||||
|
|
||||||
|
int currentInt;
|
||||||
|
int currentIntBitPosition;
|
||||||
|
int bitData;
|
||||||
|
int cpos;
|
||||||
|
int j;
|
||||||
|
final int l = text.length;
|
||||||
|
for (int i = 0; i < l; i++) {
|
||||||
|
cpos = (i * (currentFont.charW + 1));
|
||||||
|
final int charIndex = text[i];
|
||||||
|
for (int dy = 0; dy < currentFont.charH; dy++) {
|
||||||
|
for (int dx = 0; dx < currentFont.charW; dx++) {
|
||||||
|
j = x + cpos + dx;
|
||||||
|
if (j > 0 & j < screenSize[0]) {
|
||||||
|
final int bit = dx + dy * currentFont.charW;
|
||||||
|
currentInt = (int) (Math.floor(bit) / (CPUFont.intBits));
|
||||||
|
currentIntBitPosition = bit - (currentInt * CPUFont.intBits);
|
||||||
|
bitData = (currentFont.chars32[charIndex * currentFont.charIntCount + currentInt] >> currentIntBitPosition) & 1;
|
||||||
|
screenPos = x + cpos + dx + (y + dy) * screenSize[0];
|
||||||
|
if (bitData == 1 & screenLength > screenPos) {
|
||||||
|
screen[screenPos] = color;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return pixels;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void glDrawStringLeft(int x, int y, String text) {
|
|
||||||
x+=Main.screenPos[0];
|
|
||||||
y+=Main.screenPos[1];
|
|
||||||
final int[] chars = currentFont.getCharIndexes(text);
|
|
||||||
currentFont.drawText(canvas2d, size, x, y, chars, color);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glDrawStringCenter(int x, int y, String text) {
|
public void glDrawStringCenter(int x, int y, String text) {
|
||||||
glDrawStringLeft(x - (glGetStringWidth(currentFont, text) / 2), y, text);
|
glDrawStringLeft(x - (currentFont.getStringWidth(text) / 2), y, text);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void glDrawStringRight(int x, int y, String text) {
|
public void glDrawStringRight(int x, int y, String text) {
|
||||||
glDrawStringLeft(x - glGetStringWidth(currentFont, text), y, text);
|
glDrawStringLeft(x - currentFont.getStringWidth(text), y, text);
|
||||||
}
|
|
||||||
|
|
||||||
public void glSetFont(RAWFont font) {
|
|
||||||
if (currentFont != font) {
|
|
||||||
currentFont = font;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int glGetStringWidth(RAWFont rf, String text) {
|
|
||||||
int w =(rf.charW+1)*text.length();
|
|
||||||
if (text.length() > 0) {
|
|
||||||
return w-1;
|
|
||||||
} else {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
// return text.length()*6;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Deprecated
|
||||||
public int glGetFontWidth(FontMetrics fm, String text) {
|
public int glGetFontWidth(FontMetrics fm, String text) {
|
||||||
return fm.stringWidth(text);
|
return fm.stringWidth(text);
|
||||||
}
|
}
|
||||||
@ -307,6 +381,21 @@ public class CPUDisplay implements Display {
|
|||||||
return currentFont;
|
return currentFont;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glColor3f(float red, float green, float blue) {
|
||||||
|
glColor3i((int) (red * 255f), (int) (green * 255f), (int) (blue * 255f));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glColor4f(float red, float green, float blue, float alpha) {
|
||||||
|
glColor4i((int) (red * 255f), (int) (green * 255f), (int) (blue * 255f), (int) (alpha * 255f));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glClearSkin() {
|
||||||
|
currentSkin = null;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -320,7 +409,33 @@ public class CPUDisplay implements Display {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Renderer getRenderer() {
|
public CPURenderer getRenderer() {
|
||||||
return new Render();
|
return r;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public RAWFont loadFont(String file) throws IOException {
|
||||||
|
return new CPUFont(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public RAWSkin loadSkin(String file) throws IOException {
|
||||||
|
return new CPUSkin(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void waitUntilExit() {
|
||||||
|
try {
|
||||||
|
do {
|
||||||
|
Thread.sleep(500);
|
||||||
|
} while(initialized);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isSupported() {
|
||||||
|
return GraphicsEnvironment.isHeadless() == false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
182
src/org/warp/picalculator/gui/graphicengine/cpu/CPUFont.java
Normal file
182
src/org/warp/picalculator/gui/graphicengine/cpu/CPUFont.java
Normal file
@ -0,0 +1,182 @@
|
|||||||
|
package org.warp.picalculator.gui.graphicengine.cpu;
|
||||||
|
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.awt.image.DataBufferInt;
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.lang.ref.WeakReference;
|
||||||
|
import java.net.URL;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
import java.util.logging.Logger;
|
||||||
|
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
|
import org.warp.picalculator.Utils;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay.CPURenderer;
|
||||||
|
|
||||||
|
public class CPUFont implements RAWFont {
|
||||||
|
|
||||||
|
public boolean[][] rawchars;
|
||||||
|
public int[] chars32;
|
||||||
|
public int minBound = 10;
|
||||||
|
public int maxBound = 0;
|
||||||
|
public int charW;
|
||||||
|
public int charH;
|
||||||
|
public int charS;
|
||||||
|
public int charIntCount;
|
||||||
|
public static final int intBits = 31;
|
||||||
|
|
||||||
|
CPUFont(String file) throws IOException {
|
||||||
|
load(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static CPUFont loadTemporaryFont(String name) throws IOException {
|
||||||
|
return new CPUFont(name);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void load(String name) throws IOException {
|
||||||
|
loadFont("/font_" + name + ".rft");
|
||||||
|
chars32 = new int[(maxBound - minBound) * charIntCount];
|
||||||
|
for (int charIndex = 0; charIndex < maxBound - minBound; charIndex++) {
|
||||||
|
final boolean[] currentChar = rawchars[charIndex];
|
||||||
|
if (currentChar == null) {
|
||||||
|
int currentInt = 0;
|
||||||
|
int currentBit = 0;
|
||||||
|
for (int i = 0; i < charS; i++) {
|
||||||
|
if (currentInt * intBits + currentBit >= (currentInt + 1) * intBits) {
|
||||||
|
currentInt += 1;
|
||||||
|
currentBit = 0;
|
||||||
|
}
|
||||||
|
chars32[charIndex * charIntCount + currentInt] = (chars32[charIndex * charIntCount + currentInt] << 1) + 1;
|
||||||
|
currentBit += 1;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
int currentInt = 0;
|
||||||
|
int currentBit = 0;
|
||||||
|
for (int i = 0; i < charS; i++) {
|
||||||
|
if (currentBit >= intBits) {
|
||||||
|
currentInt += 1;
|
||||||
|
currentBit = 0;
|
||||||
|
}
|
||||||
|
chars32[charIndex * charIntCount + currentInt] = (chars32[charIndex * charIntCount + currentInt]) | ((currentChar[i] ? 1 : 0) << currentBit);
|
||||||
|
currentBit++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Object obj = new Object();
|
||||||
|
final WeakReference<Object> ref = new WeakReference<>(obj);
|
||||||
|
obj = null;
|
||||||
|
while (ref.get() != null) {
|
||||||
|
System.gc();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void loadFont(String string) throws IOException {
|
||||||
|
final URL res = this.getClass().getResource(string);
|
||||||
|
final int[] file = Utils.realBytes(Utils.convertStreamToByteArray(res.openStream(), res.getFile().length()));
|
||||||
|
final int filelength = file.length;
|
||||||
|
if (filelength >= 16) {
|
||||||
|
if (file[0x0] == 114 && file[0x1] == 97 && file[0x2] == 119 && file[0x3] == 0xFF && file[0x8] == 0xFF && file[0xD] == 0xFF) {
|
||||||
|
charW = file[0x4] << 8 | file[0x5];
|
||||||
|
charH = file[0x6] << 8 | file[0x7];
|
||||||
|
charS = charW * charH;
|
||||||
|
charIntCount = (int) Math.ceil(((double) charS) / ((double) intBits));
|
||||||
|
minBound = file[0x9] << 24 | file[0xA] << 16 | file[0xB] << 8 | file[0xC];
|
||||||
|
maxBound = file[0xE] << 24 | file[0xF] << 16 | file[0x10] << 8 | file[0x11];
|
||||||
|
if (maxBound <= minBound) {
|
||||||
|
maxBound = 9900; //TODO remove it: temp fix
|
||||||
|
}
|
||||||
|
rawchars = new boolean[maxBound - minBound][];
|
||||||
|
int index = 0x12;
|
||||||
|
while (index < filelength) {
|
||||||
|
try {
|
||||||
|
final int charIndex = file[index] << 8 | file[index + 1];
|
||||||
|
final boolean[] rawchar = new boolean[charS];
|
||||||
|
int charbytescount = 0;
|
||||||
|
while (charbytescount * 8 < charS) {
|
||||||
|
charbytescount += 1;
|
||||||
|
}
|
||||||
|
int currentBit = 0;
|
||||||
|
for (int i = 0; i <= charbytescount; i++) {
|
||||||
|
for (int bit = 0; bit < 8; bit++) {
|
||||||
|
if (currentBit >= charS) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
rawchar[currentBit] = (((file[index + 2 + i] >> (8 - 1 - bit)) & 0x1) == 1) ? true : false;
|
||||||
|
currentBit++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
rawchars[charIndex - minBound] = rawchar;
|
||||||
|
index += 2 + charbytescount;
|
||||||
|
} catch (final Exception ex) {
|
||||||
|
ex.printStackTrace();
|
||||||
|
System.out.println(string);
|
||||||
|
System.exit(-1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new IOException();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw new IOException();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("unused")
|
||||||
|
private void saveArray(int[] screen, String coutputpng) {
|
||||||
|
final BufferedImage bi = new BufferedImage(300, 200, BufferedImage.TYPE_INT_RGB);
|
||||||
|
final int[] a = ((DataBufferInt) bi.getRaster().getDataBuffer()).getData();
|
||||||
|
System.arraycopy(screen, 0, a, 0, screen.length);
|
||||||
|
try {
|
||||||
|
ImageIO.write(bi, "PNG", new File(coutputpng));
|
||||||
|
} catch (final IOException ex) {
|
||||||
|
Logger.getLogger(RAWFont.class.getName()).log(Level.SEVERE, null, ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public int[] getCharIndexes(String txt) {
|
||||||
|
final int l = txt.length();
|
||||||
|
final int[] indexes = new int[l];
|
||||||
|
final char[] chars = txt.toCharArray();
|
||||||
|
for (int i = 0; i < l; i++) {
|
||||||
|
indexes[i] = (chars[i] & 0xFFFF) - minBound;
|
||||||
|
}
|
||||||
|
return indexes;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void initialize(Display d) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void use(Display d) {
|
||||||
|
((CPURenderer) d.getRenderer()).currentFont = this;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getStringWidth(String text) {
|
||||||
|
final int w = (charW + 1) * text.length();
|
||||||
|
if (text.length() > 0) {
|
||||||
|
return w - 1;
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getCharacterWidth() {
|
||||||
|
return charW;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getCharacterHeight() {
|
||||||
|
return charH;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
53
src/org/warp/picalculator/gui/graphicengine/cpu/CPUSkin.java
Normal file
53
src/org/warp/picalculator/gui/graphicengine/cpu/CPUSkin.java
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
package org.warp.picalculator.gui.graphicengine.cpu;
|
||||||
|
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
|
import org.warp.picalculator.Main;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay.CPURenderer;
|
||||||
|
|
||||||
|
public class CPUSkin implements RAWSkin {
|
||||||
|
|
||||||
|
public int[] skinData;
|
||||||
|
public int[] skinSize;
|
||||||
|
|
||||||
|
CPUSkin(String file) throws IOException {
|
||||||
|
load(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void load(String file) throws IOException {
|
||||||
|
final BufferedImage img = ImageIO.read(Main.instance.getClass().getResource("/"+file));
|
||||||
|
skinData = getMatrixOfImage(img);
|
||||||
|
skinSize = new int[] { img.getWidth(), img.getHeight() };
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int[] getMatrixOfImage(BufferedImage bufferedImage) {
|
||||||
|
final int width = bufferedImage.getWidth(null);
|
||||||
|
final int height = bufferedImage.getHeight(null);
|
||||||
|
final int[] pixels = new int[width * height];
|
||||||
|
for (int i = 0; i < width; i++) {
|
||||||
|
for (int j = 0; j < height; j++) {
|
||||||
|
pixels[i + j * width] = bufferedImage.getRGB(i, j);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return pixels;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void initialize(Display d) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void use(Display d) {
|
||||||
|
((CPURenderer) d.getRenderer()).currentSkin = this;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -18,7 +18,7 @@ import javax.swing.JPanel;
|
|||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.device.Keyboard;
|
import org.warp.picalculator.device.Keyboard;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.Drawable;
|
import org.warp.picalculator.gui.graphicengine.Drawable;
|
||||||
|
|
||||||
public class SwingWindow extends JFrame {
|
public class SwingWindow extends JFrame {
|
||||||
@ -26,40 +26,41 @@ public class SwingWindow extends JFrame {
|
|||||||
public CustomCanvas c;
|
public CustomCanvas c;
|
||||||
private static Drawable d;
|
private static Drawable d;
|
||||||
public boolean wasResized = false;
|
public boolean wasResized = false;
|
||||||
|
private final CPUDisplay display;
|
||||||
|
|
||||||
public SwingWindow(Drawable d) {
|
public SwingWindow(CPUDisplay disp, Drawable d) {
|
||||||
SwingWindow.d = d;
|
SwingWindow.d = d;
|
||||||
|
display = disp;
|
||||||
c = new CustomCanvas();
|
c = new CustomCanvas();
|
||||||
c.setDoubleBuffered(false);
|
c.setDoubleBuffered(false);
|
||||||
this.add(c);
|
this.add(c);
|
||||||
// this.setExtendedState(Frame.MAXIMIZED_BOTH);
|
// this.setExtendedState(Frame.MAXIMIZED_BOTH);
|
||||||
Toolkit.getDefaultToolkit().setDynamicLayout(false);
|
Toolkit.getDefaultToolkit().setDynamicLayout(false);
|
||||||
// Transparent 16 x 16 pixel cursor image.
|
// Transparent 16 x 16 pixel cursor image.
|
||||||
BufferedImage cursorImg = new BufferedImage(16, 16, BufferedImage.TYPE_INT_ARGB);
|
final BufferedImage cursorImg = new BufferedImage(16, 16, BufferedImage.TYPE_INT_ARGB);
|
||||||
|
|
||||||
if (Utils.debugOn) {
|
if (Utils.debugOn) {
|
||||||
if (Utils.debugThirdScreen) {
|
if (Utils.debugThirdScreen) {
|
||||||
this.setLocation(2880, 900);
|
this.setLocation(2880, 900);
|
||||||
this.setResizable(false);
|
setResizable(false);
|
||||||
this.setAlwaysOnTop(true);
|
setAlwaysOnTop(true);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// Create a new blank cursor.
|
// Create a new blank cursor.
|
||||||
Cursor blankCursor = Toolkit.getDefaultToolkit().createCustomCursor(cursorImg, new Point(0, 0), "blank cursor");
|
final Cursor blankCursor = Toolkit.getDefaultToolkit().createCustomCursor(cursorImg, new Point(0, 0), "blank cursor");
|
||||||
|
|
||||||
// Set the blank cursor to the JFrame.
|
// Set the blank cursor to the JFrame.
|
||||||
getContentPane().setCursor(blankCursor);
|
getContentPane().setCursor(blankCursor);
|
||||||
|
|
||||||
this.setResizable(false);
|
setResizable(false);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.setTitle("Raspberry PI Calculator by XDrake99 (Andrea Cavalli)");
|
setTitle("Raspberry PI Calculator by XDrake99 (Andrea Cavalli)");
|
||||||
|
|
||||||
|
addComponentListener(new ComponentListener() {
|
||||||
this.addComponentListener(new ComponentListener() {
|
|
||||||
@Override
|
@Override
|
||||||
public void componentHidden(ComponentEvent e) {
|
public void componentHidden(ComponentEvent e) {
|
||||||
PIDisplay.display.destroy();
|
DisplayManager.display.destroy();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -73,10 +74,10 @@ public class SwingWindow extends JFrame {
|
|||||||
@Override
|
@Override
|
||||||
public void componentShown(ComponentEvent e) {}
|
public void componentShown(ComponentEvent e) {}
|
||||||
});
|
});
|
||||||
this.addKeyListener(new KeyListener() {
|
addKeyListener(new KeyListener() {
|
||||||
@Override
|
@Override
|
||||||
public void keyPressed(KeyEvent arg0) {
|
public void keyPressed(KeyEvent arg0) {
|
||||||
Keyboard.debugKeyEvent = arg0;
|
Keyboard.debugKeyCode = arg0.getKeyCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -125,7 +126,7 @@ public class SwingWindow extends JFrame {
|
|||||||
}
|
}
|
||||||
int row = 2;
|
int row = 2;
|
||||||
int col = 1;
|
int col = 1;
|
||||||
Keyboard.debugKeysDown[row-1][col-1] = false;
|
Keyboard.debugKeysDown[row - 1][col - 1] = false;
|
||||||
break;
|
break;
|
||||||
case KeyEvent.VK_1:
|
case KeyEvent.VK_1:
|
||||||
if (!Keyboard.shift && !Keyboard.alpha) {
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
@ -175,12 +176,12 @@ public class SwingWindow extends JFrame {
|
|||||||
//LEFT
|
//LEFT
|
||||||
row = 2;
|
row = 2;
|
||||||
col = 3;
|
col = 3;
|
||||||
Keyboard.debugKeysDown[row-1][col-1] = false;
|
Keyboard.debugKeysDown[row - 1][col - 1] = false;
|
||||||
case KeyEvent.VK_RIGHT:
|
case KeyEvent.VK_RIGHT:
|
||||||
//RIGHT
|
//RIGHT
|
||||||
row = 2;
|
row = 2;
|
||||||
col = 5;
|
col = 5;
|
||||||
Keyboard.debugKeysDown[row-1][col-1] = false;
|
Keyboard.debugKeysDown[row - 1][col - 1] = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -216,7 +217,7 @@ public class SwingWindow extends JFrame {
|
|||||||
|
|
||||||
// private static ArrayList<Double> mediaValori = new ArrayList<Double>();
|
// private static ArrayList<Double> mediaValori = new ArrayList<Double>();
|
||||||
|
|
||||||
public static class CustomCanvas extends JPanel {
|
public class CustomCanvas extends JPanel {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
@ -228,11 +229,11 @@ public class SwingWindow extends JFrame {
|
|||||||
// long time1 = System.nanoTime();
|
// long time1 = System.nanoTime();
|
||||||
d.refresh();
|
d.refresh();
|
||||||
|
|
||||||
final int[] a = ((DataBufferInt) CPUDisplay.g.getRaster().getDataBuffer()).getData();
|
final int[] a = ((DataBufferInt) display.g.getRaster().getDataBuffer()).getData();
|
||||||
// System.arraycopy(canvas2d, 0, a, 0, canvas2d.length);
|
// System.arraycopy(canvas2d, 0, a, 0, canvas2d.length);
|
||||||
CPUDisplay.canvas2d = a;
|
CPUDisplay.canvas2d = a;
|
||||||
g.clearRect(0, 0, CPUDisplay.size[0], CPUDisplay.size[1]);
|
g.clearRect(0, 0, display.size[0], display.size[1]);
|
||||||
g.drawImage(CPUDisplay.g, 0, 0, null);
|
g.drawImage(display.g, 0, 0, null);
|
||||||
// long time2 = System.nanoTime();
|
// long time2 = System.nanoTime();
|
||||||
// double timeDelta = ((double)(time2-time1))/1000000000d;
|
// double timeDelta = ((double)(time2-time1))/1000000000d;
|
||||||
// double mediaAttuale = timeDelta;
|
// double mediaAttuale = timeDelta;
|
||||||
|
@ -1,673 +0,0 @@
|
|||||||
/**
|
|
||||||
* Copyright 2012-2013 JogAmp Community. All rights reserved.
|
|
||||||
*
|
|
||||||
* Redistribution and use in source and binary forms, with or without modification, are
|
|
||||||
* permitted provided that the following conditions are met:
|
|
||||||
*
|
|
||||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
|
||||||
* conditions and the following disclaimer.
|
|
||||||
*
|
|
||||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
|
||||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
|
||||||
* provided with the distribution.
|
|
||||||
*
|
|
||||||
* THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
|
||||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
|
||||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
|
|
||||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
|
||||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
|
||||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
|
||||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
|
||||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
*
|
|
||||||
* The views and conclusions contained in the software and documentation are those of the
|
|
||||||
* authors and should not be interpreted as representing official policies, either expressed
|
|
||||||
* or implied, of JogAmp Community.
|
|
||||||
*/
|
|
||||||
|
|
||||||
package org.warp.picalculator.gui.graphicengine.gpu;
|
|
||||||
|
|
||||||
import com.jogamp.opengl.GL;
|
|
||||||
import com.jogamp.opengl.GL2ES1;
|
|
||||||
import com.jogamp.opengl.GL2ES2;
|
|
||||||
import com.jogamp.opengl.GLAutoDrawable;
|
|
||||||
import com.jogamp.opengl.GLEventListener;
|
|
||||||
import com.jogamp.opengl.GLException;
|
|
||||||
import com.jogamp.opengl.GLProfile;
|
|
||||||
import com.jogamp.opengl.GLCapabilities;
|
|
||||||
import com.jogamp.newt.opengl.GLWindow;
|
|
||||||
|
|
||||||
import com.jogamp.opengl.util.*;
|
|
||||||
import com.jogamp.opengl.util.texture.Texture;
|
|
||||||
import com.jogamp.opengl.util.texture.TextureIO;
|
|
||||||
import com.jogamp.common.nio.Buffers;
|
|
||||||
|
|
||||||
import java.io.ByteArrayInputStream;
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.nio.FloatBuffer;
|
|
||||||
|
|
||||||
import javax.imageio.ImageIO;
|
|
||||||
|
|
||||||
import org.warp.picalculator.gui.graphicengine.Display;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* <pre>
|
|
||||||
* __ __|_ ___________________________________________________________________________ ___|__ __
|
|
||||||
* // /\ _ /\ \\
|
|
||||||
* //____/ \__ __ _____ _____ _____ _____ _____ | | __ _____ _____ __ __/ \____\\
|
|
||||||
* \ \ / / __| | | __| _ | | _ | | | __| | | __| | /\ \ / /
|
|
||||||
* \____\/_/ | | | | | | | | | | | __| | | | | | | | | | |__ " \_\/____/
|
|
||||||
* /\ \ |_____|_____|_____|__|__|_|_|_|__| | | |_____|_____|_____|_____| _ / /\
|
|
||||||
* / \____\ http://jogamp.org |_| /____/ \
|
|
||||||
* \ / "' _________________________________________________________________________ `" \ /
|
|
||||||
* \/____. .____\/
|
|
||||||
* </pre>
|
|
||||||
*
|
|
||||||
* <p>
|
|
||||||
* JOGL2 OpenGL ES 2 demo to expose and learn what the RAW OpenGL ES 2 API looks like.
|
|
||||||
*
|
|
||||||
* Compile, run and enjoy:
|
|
||||||
wget http://jogamp.org/deployment/jogamp-current/archive/jogamp-all-platforms.7z
|
|
||||||
7z x jogamp-all-platforms.7z
|
|
||||||
cd jogamp-all-platforms
|
|
||||||
mkdir -p demos/es2
|
|
||||||
cd demos/es2
|
|
||||||
wget https://raw.github.com/xranby/jogl-demos/master/src/demos/es2/RawGL2ES2demo.java
|
|
||||||
cd ../..
|
|
||||||
javac -cp jar/jogl-all.jar:jar/gluegen-rt.jar demos/es2/RawGL2ES2demo.java
|
|
||||||
java -cp jar/jogl-all.jar:jar/gluegen-rt.jar:. demos.es2.RawGL2ES2demo
|
|
||||||
* </p>
|
|
||||||
*
|
|
||||||
*
|
|
||||||
* @author Xerxes Rånby (xranby)
|
|
||||||
*/
|
|
||||||
|
|
||||||
public class CalculatorWindow implements GLEventListener{
|
|
||||||
|
|
||||||
/* Introducing the OpenGL ES 2 Vertex shader
|
|
||||||
*
|
|
||||||
* The main loop inside the vertex shader gets executed
|
|
||||||
* one time for each vertex.
|
|
||||||
*
|
|
||||||
* vertex -> * uniform data -> mat4 projection = ( 1, 0, 0, 0,
|
|
||||||
* (0,1,0) / \ 0, 1, 0, 0,
|
|
||||||
* / . \ <- origo (0,0,0) 0, 0, 1, 0,
|
|
||||||
* / \ 0, 0,-1, 1 );
|
|
||||||
* vertex -> *-------* <- vertex
|
|
||||||
* (-1,-1,0) (1,-1,0) <- attribute data can be used
|
|
||||||
* (0, 0,1) for color, position, normals etc.
|
|
||||||
*
|
|
||||||
* The vertex shader recive input data in form of
|
|
||||||
* "uniform" data that are common to all vertex
|
|
||||||
* and
|
|
||||||
* "attribute" data that are individual to each vertex.
|
|
||||||
* One vertex can have several "attribute" data sources enabled.
|
|
||||||
*
|
|
||||||
* The vertex shader produce output used by the fragment shader.
|
|
||||||
* gl_Position are expected to get set to the final vertex position.
|
|
||||||
* You can also send additional user defined
|
|
||||||
* "varying" data to the fragment shader.
|
|
||||||
*
|
|
||||||
* Model Translate, Scale and Rotate are done here by matrix-multiplying a
|
|
||||||
* projection matrix against each vertex position.
|
|
||||||
*
|
|
||||||
* The whole vertex shader program are a String containing GLSL ES language
|
|
||||||
* http://www.khronos.org/registry/gles/specs/2.0/GLSL_ES_Specification_1.0.17.pdf
|
|
||||||
* sent to the GPU driver for compilation.
|
|
||||||
*/
|
|
||||||
private String vertexShaderString =
|
|
||||||
// For GLSL 1 and 1.1 code i highly recomend to not include a
|
|
||||||
// GLSL ES language #version line, GLSL ES section 3.4
|
|
||||||
// Many GPU drivers refuse to compile the shader if #version is different from
|
|
||||||
// the drivers internal GLSL version.
|
|
||||||
//
|
|
||||||
// This demo use GLSL version 1.1 (the implicit version)
|
|
||||||
|
|
||||||
"#if __VERSION__ >= 130\n" + // GLSL 130+ uses in and out
|
|
||||||
" #define attribute in\n" + // instead of attribute and varying
|
|
||||||
" #define varying out\n" + // used by OpenGL 3 core and later.
|
|
||||||
"#endif\n" +
|
|
||||||
|
|
||||||
"#ifdef GL_ES \n" +
|
|
||||||
"precision mediump float; \n" + // Precision Qualifiers
|
|
||||||
"precision mediump int; \n" + // GLSL ES section 4.5.2
|
|
||||||
"#endif \n" +
|
|
||||||
|
|
||||||
"uniform mat4 uniform_Projection; \n" + // Incomming data used by
|
|
||||||
"attribute vec4 attribute_Position; \n" + // the vertex shader
|
|
||||||
"attribute vec4 attribute_Color; \n" + // uniform and attributes
|
|
||||||
"attribute vec2 a_TexCoordinate; \n" +
|
|
||||||
|
|
||||||
"varying vec2 v_TexCoordinate; \n" +
|
|
||||||
"varying vec4 varying_Color; \n" + // Outgoing varying data
|
|
||||||
// sent to the fragment shader
|
|
||||||
"void main(void) \n" +
|
|
||||||
"{ \n" +
|
|
||||||
" varying_Color = attribute_Color; \n" +
|
|
||||||
" v_TexCoordinate = a_TexCoordinate; \n" +
|
|
||||||
" gl_Position = uniform_Projection * attribute_Position; \n" +
|
|
||||||
"} ";
|
|
||||||
|
|
||||||
/* Introducing the OpenGL ES 2 Fragment shader
|
|
||||||
*
|
|
||||||
* The main loop of the fragment shader gets executed for each visible
|
|
||||||
* pixel fragment on the render buffer.
|
|
||||||
*
|
|
||||||
* vertex-> *
|
|
||||||
* (0,1,-1) /f\
|
|
||||||
* /ffF\ <- This fragment F gl_FragCoord get interpolated
|
|
||||||
* /fffff\ to (0.25,0.25,-1) based on the
|
|
||||||
* vertex-> *fffffff* <-vertex three vertex gl_Position.
|
|
||||||
* (-1,-1,-1) (1,-1,-1)
|
|
||||||
*
|
|
||||||
*
|
|
||||||
* All incomming "varying" and gl_FragCoord data to the fragment shader
|
|
||||||
* gets interpolated based on the vertex positions.
|
|
||||||
*
|
|
||||||
* The fragment shader produce and store the final color data output into
|
|
||||||
* gl_FragColor.
|
|
||||||
*
|
|
||||||
* Is up to you to set the final colors and calculate lightning here based on
|
|
||||||
* supplied position, color and normal data.
|
|
||||||
*
|
|
||||||
* The whole fragment shader program are a String containing GLSL ES language
|
|
||||||
* http://www.khronos.org/registry/gles/specs/2.0/GLSL_ES_Specification_1.0.17.pdf
|
|
||||||
* sent to the GPU driver for compilation.
|
|
||||||
*/
|
|
||||||
private String fragmentShaderString =
|
|
||||||
"#if __VERSION__ >= 130\n" +
|
|
||||||
" #define varying in\n" +
|
|
||||||
" out vec4 mgl_FragColor;\n" +
|
|
||||||
" #define texture2D texture\n" +
|
|
||||||
" #define gl_FragColor mgl_FragColor\n" +
|
|
||||||
"#endif\n" +
|
|
||||||
|
|
||||||
"#ifdef GL_ES \n" +
|
|
||||||
"precision mediump float; \n" +
|
|
||||||
"precision mediump int; \n" +
|
|
||||||
"#endif \n" +
|
|
||||||
|
|
||||||
"uniform sampler2D u_Texture; \n" +
|
|
||||||
|
|
||||||
"varying vec2 v_TexCoordinate; \n" +
|
|
||||||
"varying vec4 varying_Color; \n" + //incomming varying data to the
|
|
||||||
//frament shader
|
|
||||||
//sent from the vertex shader
|
|
||||||
"void main (void) \n" +
|
|
||||||
"{ \n" +
|
|
||||||
|
|
||||||
" gl_FragColor = (varying_Color * texture2D(u_Texture, v_TexCoordinate));" +
|
|
||||||
"} ";
|
|
||||||
|
|
||||||
|
|
||||||
FloatBuffer fbVertices = Buffers.newDirectFloatBuffer(2000*18); // max 2000 quadrati
|
|
||||||
FloatBuffer fbColors = Buffers.newDirectFloatBuffer(2000*24); // max 2000 quadrati
|
|
||||||
FloatBuffer fbTextureCoordinates = Buffers.newDirectFloatBuffer(2000*12); // max 2000 quadrati
|
|
||||||
final Texture[] texture = new Texture[1];
|
|
||||||
final int[] textureHandle = new int[1];
|
|
||||||
|
|
||||||
private final Display disp;
|
|
||||||
public CalculatorWindow(Display disp) {
|
|
||||||
this.disp = disp;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Introducing projection matrix helper functions
|
|
||||||
*
|
|
||||||
* OpenGL ES 2 vertex projection transformations gets applied inside the
|
|
||||||
* vertex shader, all you have to do are to calculate and supply a projection matrix.
|
|
||||||
*
|
|
||||||
* Its recomended to use the com/jogamp/opengl/util/PMVMatrix.java
|
|
||||||
* import com.jogamp.opengl.util.PMVMatrix;
|
|
||||||
* To simplify all your projection model view matrix creation needs.
|
|
||||||
*
|
|
||||||
* These helpers here are based on PMVMatrix code and common linear
|
|
||||||
* algebra for matrix multiplication, translate and rotations.
|
|
||||||
*/
|
|
||||||
private void glMultMatrixf(FloatBuffer a, FloatBuffer b, FloatBuffer d) {
|
|
||||||
final int aP = a.position();
|
|
||||||
final int bP = b.position();
|
|
||||||
final int dP = d.position();
|
|
||||||
for (int i = 0; i < 4; i++) {
|
|
||||||
final float ai0=a.get(aP+i+0*4), ai1=a.get(aP+i+1*4), ai2=a.get(aP+i+2*4), ai3=a.get(aP+i+3*4);
|
|
||||||
d.put(dP+i+0*4 , ai0 * b.get(bP+0+0*4) + ai1 * b.get(bP+1+0*4) + ai2 * b.get(bP+2+0*4) + ai3 * b.get(bP+3+0*4) );
|
|
||||||
d.put(dP+i+1*4 , ai0 * b.get(bP+0+1*4) + ai1 * b.get(bP+1+1*4) + ai2 * b.get(bP+2+1*4) + ai3 * b.get(bP+3+1*4) );
|
|
||||||
d.put(dP+i+2*4 , ai0 * b.get(bP+0+2*4) + ai1 * b.get(bP+1+2*4) + ai2 * b.get(bP+2+2*4) + ai3 * b.get(bP+3+2*4) );
|
|
||||||
d.put(dP+i+3*4 , ai0 * b.get(bP+0+3*4) + ai1 * b.get(bP+1+3*4) + ai2 * b.get(bP+2+3*4) + ai3 * b.get(bP+3+3*4) );
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private float[] multiply(float[] a,float[] b){
|
|
||||||
float[] tmp = new float[16];
|
|
||||||
glMultMatrixf(FloatBuffer.wrap(a),FloatBuffer.wrap(b),FloatBuffer.wrap(tmp));
|
|
||||||
return tmp;
|
|
||||||
}
|
|
||||||
|
|
||||||
private float[] translate(float[] m,float x,float y,float z){
|
|
||||||
float[] t = { 1.0f, 0.0f, 0.0f, 0.0f,
|
|
||||||
0.0f, 1.0f, 0.0f, 0.0f,
|
|
||||||
0.0f, 0.0f, 1.0f, 0.0f,
|
|
||||||
x, y, z, 1.0f };
|
|
||||||
return multiply(m, t);
|
|
||||||
}
|
|
||||||
|
|
||||||
private float[] rotate(float[] m,float a,float x,float y,float z){
|
|
||||||
float s, c;
|
|
||||||
s = (float)Math.sin(Math.toRadians(a));
|
|
||||||
c = (float)Math.cos(Math.toRadians(a));
|
|
||||||
float[] r = {
|
|
||||||
x * x * (1.0f - c) + c, y * x * (1.0f - c) + z * s, x * z * (1.0f - c) - y * s, 0.0f,
|
|
||||||
x * y * (1.0f - c) - z * s, y * y * (1.0f - c) + c, y * z * (1.0f - c) + x * s, 0.0f,
|
|
||||||
x * z * (1.0f - c) + y * s, y * z * (1.0f - c) - x * s, z * z * (1.0f - c) + c, 0.0f,
|
|
||||||
0.0f, 0.0f, 0.0f, 1.0f };
|
|
||||||
return multiply(m, r);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Introducing the GL2ES2 demo
|
|
||||||
*
|
|
||||||
* How to render a triangle using ~500 lines of code using the RAW
|
|
||||||
* OpenGL ES 2 API.
|
|
||||||
* The Programmable pipeline in OpenGL ES 2 are both fast and flexible
|
|
||||||
* yet it do take some extra lines of code to setup.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
private double t0 = System.currentTimeMillis();
|
|
||||||
private double theta;
|
|
||||||
private double s;
|
|
||||||
|
|
||||||
private static int width=1920;
|
|
||||||
private static int height=1080;
|
|
||||||
|
|
||||||
private int shaderProgram;
|
|
||||||
private int vertShader;
|
|
||||||
private int fragShader;
|
|
||||||
private int ModelViewProjectionMatrixHandle;
|
|
||||||
private int mTextureUniformHandle;
|
|
||||||
private int mTextureCoordinateHandle;
|
|
||||||
private final int mTextureCoordinateDataSize = 2;
|
|
||||||
private int mTextureDataHandle;
|
|
||||||
static final int COLOR_IDX = 0;
|
|
||||||
static final int VERTICES_IDX = 1;
|
|
||||||
static final int TEXTURE_IDX = 2;
|
|
||||||
int[] vboHandles;
|
|
||||||
|
|
||||||
public GLWindow window;
|
|
||||||
|
|
||||||
public void create(){
|
|
||||||
/* This demo are based on the GL2ES2 GLProfile that uses common hardware acceleration
|
|
||||||
* functionality of desktop OpenGL 3, 2 and mobile OpenGL ES 2 devices.
|
|
||||||
* JogAmp JOGL will probe all the installed libGL.so, libEGL.so and libGLESv2.so librarys on
|
|
||||||
* the system to find which one provide hardware acceleration for your GPU device.
|
|
||||||
* Its common to find more than one version of these librarys installed on a system.
|
|
||||||
* For example on a ARM Linux system JOGL may find
|
|
||||||
* Hardware accelerated Nvidia tegra GPU drivers in: /usr/lib/nvidia-tegra/libEGL.so
|
|
||||||
* Software rendered Mesa Gallium driver in: /usr/lib/arm-linux-gnueabi/mesa-egl/libEGL.so.1
|
|
||||||
* Software rendered Mesa X11 in: /usr/lib/arm-linux-gnueabi/mesa/libGL.so
|
|
||||||
* Good news!: JOGL does all this probing for you all you have to do are to ask for
|
|
||||||
* the GLProfile you want to use.
|
|
||||||
*/
|
|
||||||
|
|
||||||
GLCapabilities caps = new GLCapabilities(GLProfile.get(GLProfile.GL2ES2));
|
|
||||||
// We may at this point tweak the caps and request a translucent drawable
|
|
||||||
caps.setBackgroundOpaque(false);
|
|
||||||
GLWindow glWindow = GLWindow.create(caps);
|
|
||||||
window = glWindow;
|
|
||||||
|
|
||||||
/* You may combine the NEWT GLWindow inside existing Swing and AWT
|
|
||||||
* applications by encapsulating the glWindow inside a
|
|
||||||
* com.jogamp.newt.awt.NewtCanvasAWT canvas.
|
|
||||||
*
|
|
||||||
* NewtCanvasAWT newtCanvas = new NewtCanvasAWT(glWindow);
|
|
||||||
* JFrame frame = new JFrame("RAW GL2ES2 Demo inside a JFrame!");
|
|
||||||
* frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
|
|
||||||
* frame.setSize(width,height);
|
|
||||||
* frame.add(newtCanvas);
|
|
||||||
* // add some swing code if you like.
|
|
||||||
* // javax.swing.JButton b = new javax.swing.JButton();
|
|
||||||
* // b.setText("Hi");
|
|
||||||
* // frame.add(b);
|
|
||||||
* frame.setVisible(true);
|
|
||||||
*/
|
|
||||||
|
|
||||||
// In this demo we prefer to setup and view the GLWindow directly
|
|
||||||
// this allows the demo to run on -Djava.awt.headless=true systems
|
|
||||||
glWindow.setTitle("Raw GL2ES2 Demo");
|
|
||||||
|
|
||||||
// Finally we connect the GLEventListener application code to the NEWT GLWindow.
|
|
||||||
// GLWindow will call the GLEventListener init, reshape, display and dispose
|
|
||||||
// functions when needed.
|
|
||||||
glWindow.addGLEventListener(this /* GLEventListener */);
|
|
||||||
Animator animator = new Animator();
|
|
||||||
animator.add(glWindow);
|
|
||||||
animator.start();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void init(GLAutoDrawable drawable) {
|
|
||||||
GL2ES2 gl = drawable.getGL().getGL2ES2();
|
|
||||||
|
|
||||||
System.err.println("Chosen GLCapabilities: " + drawable.getChosenGLCapabilities());
|
|
||||||
System.err.println("INIT GL IS: " + gl.getClass().getName());
|
|
||||||
System.err.println("GL_VENDOR: " + gl.glGetString(GL.GL_VENDOR));
|
|
||||||
System.err.println("GL_RENDERER: " + gl.glGetString(GL.GL_RENDERER));
|
|
||||||
System.err.println("GL_VERSION: " + gl.glGetString(GL.GL_VERSION));
|
|
||||||
|
|
||||||
/* The initialization below will use the OpenGL ES 2 API directly
|
|
||||||
* to setup the two shader programs that will be run on the GPU.
|
|
||||||
*
|
|
||||||
* Its recommended to use the jogamp/opengl/util/glsl/ classes
|
|
||||||
* import com.jogamp.opengl.util.glsl.ShaderCode;
|
|
||||||
* import com.jogamp.opengl.util.glsl.ShaderProgram;
|
|
||||||
* import com.jogamp.opengl.util.glsl.ShaderState;
|
|
||||||
* to simplify shader customization, compile and loading.
|
|
||||||
*
|
|
||||||
* You may also want to look at the JOGL RedSquareES2 demo
|
|
||||||
* http://jogamp.org/git/?p=jogl.git;a=blob;f=src/test/com/jogamp/opengl/test/junit/jogl/demos/es2/RedSquareES2.java;hb=HEAD#l78
|
|
||||||
* to see how the shader customization, compile and loading is done
|
|
||||||
* using the recommended JogAmp GLSL utility classes.
|
|
||||||
*/
|
|
||||||
|
|
||||||
// Make the shader strings compatible with OpenGL 3 core if needed
|
|
||||||
// GL2ES2 also includes the intersection of GL3 core
|
|
||||||
// The default implicit GLSL version 1.1 is now depricated in GL3 core
|
|
||||||
// GLSL 1.3 is the minimum version that now has to be explicitly set.
|
|
||||||
// This allows the shaders to compile using the latest
|
|
||||||
// desktop OpenGL 3 and 4 drivers.
|
|
||||||
if(gl.isGL3core()){
|
|
||||||
System.out.println("GL3 core detected: explicit add #version 130 to shaders");
|
|
||||||
vertexShaderString = "#version 130\n"+vertexShaderString;
|
|
||||||
fragmentShaderString = "#version 130\n"+fragmentShaderString;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Create GPU shader handles
|
|
||||||
// OpenGL ES retuns a index id to be stored for future reference.
|
|
||||||
vertShader = gl.glCreateShader(GL2ES2.GL_VERTEX_SHADER);
|
|
||||||
fragShader = gl.glCreateShader(GL2ES2.GL_FRAGMENT_SHADER);
|
|
||||||
|
|
||||||
//Generate textures
|
|
||||||
gl.glGenTextures(1, textureHandle, 0);
|
|
||||||
|
|
||||||
try {
|
|
||||||
Texture t = loadTexture("test.png");
|
|
||||||
textureHandle[0] = t.getTarget();
|
|
||||||
texture[0] = t;
|
|
||||||
gl.glBindTexture(GL2ES2.GL_TEXTURE_2D, textureHandle[0]);
|
|
||||||
} catch (GLException | IOException e) {
|
|
||||||
// TODO Auto-generated catch block
|
|
||||||
e.printStackTrace();
|
|
||||||
}
|
|
||||||
|
|
||||||
//Compile the vertexShader String into a program.
|
|
||||||
String[] vlines = new String[] { vertexShaderString };
|
|
||||||
int[] vlengths = new int[] { vlines[0].length() };
|
|
||||||
gl.glShaderSource(vertShader, vlines.length, vlines, vlengths, 0);
|
|
||||||
gl.glCompileShader(vertShader);
|
|
||||||
|
|
||||||
//Check compile status.
|
|
||||||
int[] compiled = new int[1];
|
|
||||||
gl.glGetShaderiv(vertShader, GL2ES2.GL_COMPILE_STATUS, compiled,0);
|
|
||||||
if(compiled[0]!=0){System.out.println("Horray! vertex shader compiled");}
|
|
||||||
else {
|
|
||||||
int[] logLength = new int[1];
|
|
||||||
gl.glGetShaderiv(vertShader, GL2ES2.GL_INFO_LOG_LENGTH, logLength, 0);
|
|
||||||
|
|
||||||
byte[] log = new byte[logLength[0]];
|
|
||||||
gl.glGetShaderInfoLog(vertShader, logLength[0], (int[])null, 0, log, 0);
|
|
||||||
|
|
||||||
System.err.println("Error compiling the vertex shader: " + new String(log));
|
|
||||||
System.exit(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
//Compile the fragmentShader String into a program.
|
|
||||||
String[] flines = new String[] { fragmentShaderString };
|
|
||||||
int[] flengths = new int[] { flines[0].length() };
|
|
||||||
gl.glShaderSource(fragShader, flines.length, flines, flengths, 0);
|
|
||||||
gl.glCompileShader(fragShader);
|
|
||||||
|
|
||||||
//Check compile status.
|
|
||||||
gl.glGetShaderiv(fragShader, GL2ES2.GL_COMPILE_STATUS, compiled,0);
|
|
||||||
if(compiled[0]!=0){System.out.println("Horray! fragment shader compiled");}
|
|
||||||
else {
|
|
||||||
int[] logLength = new int[1];
|
|
||||||
gl.glGetShaderiv(fragShader, GL2ES2.GL_INFO_LOG_LENGTH, logLength, 0);
|
|
||||||
|
|
||||||
byte[] log = new byte[logLength[0]];
|
|
||||||
gl.glGetShaderInfoLog(fragShader, logLength[0], (int[])null, 0, log, 0);
|
|
||||||
|
|
||||||
System.err.println("Error compiling the fragment shader: " + new String(log));
|
|
||||||
System.exit(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
//Each shaderProgram must have
|
|
||||||
//one vertex shader and one fragment shader.
|
|
||||||
shaderProgram = gl.glCreateProgram();
|
|
||||||
gl.glAttachShader(shaderProgram, vertShader);
|
|
||||||
gl.glAttachShader(shaderProgram, fragShader);
|
|
||||||
|
|
||||||
//Associate attribute ids with the attribute names inside
|
|
||||||
//the vertex shader.
|
|
||||||
gl.glBindAttribLocation(shaderProgram, 0, "attribute_Position");
|
|
||||||
gl.glBindAttribLocation(shaderProgram, 1, "attribute_Color");
|
|
||||||
gl.glBindAttribLocation(shaderProgram, 2, "a_TexCoordinate");
|
|
||||||
|
|
||||||
gl.glLinkProgram(shaderProgram);
|
|
||||||
|
|
||||||
//Get a id number to the uniform_Projection matrix
|
|
||||||
//so that we can update it.
|
|
||||||
ModelViewProjectionMatrixHandle = gl.glGetUniformLocation(shaderProgram, "uniform_Projection");
|
|
||||||
mTextureUniformHandle = gl.glGetUniformLocation(shaderProgram, "u_Texture");
|
|
||||||
mTextureCoordinateHandle = gl.glGetAttribLocation(shaderProgram, "a_TexCoordinate");
|
|
||||||
|
|
||||||
/* GL2ES2 also includes the intersection of GL3 core
|
|
||||||
* GL3 core and later mandates that a "Vector Buffer Object" must
|
|
||||||
* be created and bound before calls such as gl.glDrawArrays is used.
|
|
||||||
* The VBO lines in this demo makes the code forward compatible with
|
|
||||||
* OpenGL 3 and ES 3 core and later where a default
|
|
||||||
* vector buffer object is deprecated.
|
|
||||||
*
|
|
||||||
* Generate two VBO pointers / handles
|
|
||||||
* VBO is data buffers stored inside the graphics card memory.
|
|
||||||
*/
|
|
||||||
vboHandles = new int[3];
|
|
||||||
gl.glGenBuffers(3, vboHandles, 0);
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public void reshape(GLAutoDrawable drawable, int x, int y, int z, int h) {
|
|
||||||
System.out.println("Window resized to width=" + z + " height=" + h);
|
|
||||||
width = z;
|
|
||||||
height = h;
|
|
||||||
|
|
||||||
// Get gl
|
|
||||||
GL2ES2 gl = drawable.getGL().getGL2ES2();
|
|
||||||
|
|
||||||
// Optional: Set viewport
|
|
||||||
// Render to a square at the center of the window.
|
|
||||||
gl.glViewport((width-height)/2,0,height,height);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void display(GLAutoDrawable drawable) {
|
|
||||||
// Update variables used in animation
|
|
||||||
double t1 = System.currentTimeMillis();
|
|
||||||
theta += (t1-t0)*0.005f;
|
|
||||||
t0 = t1;
|
|
||||||
s = Math.sin(theta);
|
|
||||||
|
|
||||||
// Get gl
|
|
||||||
GL2ES2 gl = drawable.getGL().getGL2ES2();
|
|
||||||
|
|
||||||
// Clear screen
|
|
||||||
gl.glClearColor(0, 0, 0, 0f); // Purple
|
|
||||||
gl.glClear(GL2ES2.GL_STENCIL_BUFFER_BIT |
|
|
||||||
GL2ES2.GL_COLOR_BUFFER_BIT |
|
|
||||||
GL2ES2.GL_DEPTH_BUFFER_BIT );
|
|
||||||
|
|
||||||
// Use the shaderProgram that got linked during the init part.
|
|
||||||
gl.glUseProgram(shaderProgram);
|
|
||||||
|
|
||||||
/* Change a projection matrix
|
|
||||||
* The matrix multiplications and OpenGL ES2 code below
|
|
||||||
* basically match this OpenGL ES1 code.
|
|
||||||
* note that the model_view_projection matrix gets sent to the vertexShader.
|
|
||||||
*
|
|
||||||
* gl.glLoadIdentity();
|
|
||||||
* gl.glTranslatef(0.0f,0.0f,-0.1f);
|
|
||||||
* gl.glRotatef((float)30f*(float)s,1.0f,0.0f,1.0f);
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
// Set the active texture unit to texture unit 0.
|
|
||||||
gl.glActiveTexture(textureHandle[0]);
|
|
||||||
|
|
||||||
// Bind the texture to this unit.
|
|
||||||
gl.glBindTexture(GL2ES2.GL_TEXTURE_2D, mTextureDataHandle);
|
|
||||||
|
|
||||||
// Tell the texture uniform sampler to use this texture in the shader by binding to texture unit 0.
|
|
||||||
gl.glUniform1i(mTextureUniformHandle, 0);
|
|
||||||
|
|
||||||
float[] model_view_projection;
|
|
||||||
float[] identity_matrix = {
|
|
||||||
1.0f, 0.0f, 0.0f, 0.0f,
|
|
||||||
0.0f, 1.0f, 0.0f, 0.0f,
|
|
||||||
0.0f, 0.0f, 1.0f, 0.0f,
|
|
||||||
0.0f, 0.0f, 0.0f, 1.0f,
|
|
||||||
};
|
|
||||||
model_view_projection = identity_matrix;
|
|
||||||
// model_view_projection = rotate(model_view_projection,30f*(float)s,1.0f,0.0f,1.0f);
|
|
||||||
// model_view_projection = translate(model_view_projection,-0.5f,-0.5f, 0f);
|
|
||||||
|
|
||||||
// Send the final projection matrix to the vertex shader by
|
|
||||||
// using the uniform location id obtained during the init part.
|
|
||||||
gl.glUniformMatrix4fv(ModelViewProjectionMatrixHandle, 1, false, model_view_projection, 0);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Render a triangle:
|
|
||||||
* The OpenGL ES2 code below basically match this OpenGL code.
|
|
||||||
*
|
|
||||||
* gl.glBegin(GL_TRIANGLES); // Drawing Using Triangles
|
|
||||||
* gl.glVertex3f( 0.0f, 1.0f, 0.0f); // Top
|
|
||||||
* gl.glVertex3f(-1.0f,-1.0f, 0.0f); // Bottom Left
|
|
||||||
* gl.glVertex3f( 1.0f,-1.0f, 0.0f); // Bottom Right
|
|
||||||
* gl.glEnd(); // Finished Drawing The Triangle
|
|
||||||
*/
|
|
||||||
|
|
||||||
fbVertices.clear();
|
|
||||||
fbColors.clear();
|
|
||||||
fbTextureCoordinates.clear();
|
|
||||||
|
|
||||||
fbVertices.put(new float[]{
|
|
||||||
0.0f, 0.0f, 0.0f, //Top
|
|
||||||
1.0f, 1.0f, 0.0f, //Bottom Left
|
|
||||||
0.0f, 1.0f, 0.0f, //Bottom Right
|
|
||||||
});
|
|
||||||
fbColors.put(new float[]{
|
|
||||||
1.0f, 0.0f, 0.0f, 1.0f, //Top color (red)
|
|
||||||
0.0f, 0.0f, 0.0f, 1.0f, //Bottom Left color (black)
|
|
||||||
1.0f, 1.0f, 0.0f, 1.0f, //Bottom Right color (yellow)
|
|
||||||
});
|
|
||||||
fbTextureCoordinates.put(new float[]{
|
|
||||||
0.0f, 0.0f,
|
|
||||||
0.0f, 1.0f,
|
|
||||||
1.0f, 0.0f,
|
|
||||||
});
|
|
||||||
fbVertices.put(new float[]{
|
|
||||||
0.0f, 0.0f, 0.0f,
|
|
||||||
1.0f, 0.0f, 0.0f,
|
|
||||||
1.0f, 1.0f, 0.0f});
|
|
||||||
fbColors.put(new float[]{
|
|
||||||
1.0f, 0.0f, 0.0f, 1.0f,
|
|
||||||
0.0f, 0.0f, 0.0f, 1.0f,
|
|
||||||
1.0f, 1.0f, 1.0f, 1.0f});
|
|
||||||
fbTextureCoordinates.put(new float[]{
|
|
||||||
0.0f, 1.0f,
|
|
||||||
1.0f, 1.0f,
|
|
||||||
1.0f, 0.0f,
|
|
||||||
});
|
|
||||||
fbColors.position(0);
|
|
||||||
fbVertices.position(0);
|
|
||||||
fbTextureCoordinates.position(0);
|
|
||||||
int numTriangles = fbVertices.limit()/9;
|
|
||||||
|
|
||||||
// Select the VBO, GPU memory data, to use for vertices
|
|
||||||
gl.glBindBuffer(GL2ES2.GL_ARRAY_BUFFER, vboHandles[VERTICES_IDX]);
|
|
||||||
|
|
||||||
// transfer data to VBO, this perform the copy of data from CPU -> GPU memory
|
|
||||||
int numBytes = numTriangles * 9 * 4;
|
|
||||||
gl.glBufferData(GL.GL_ARRAY_BUFFER, numBytes, fbVertices, GL.GL_STATIC_DRAW);
|
|
||||||
|
|
||||||
// Associate Vertex attribute 0 with the last bound VBO
|
|
||||||
gl.glVertexAttribPointer(0 /* the vertex attribute */, 3,
|
|
||||||
GL2ES2.GL_FLOAT, false /* normalized? */, 0 /* stride */,
|
|
||||||
0 /* The bound VBO data offset */);
|
|
||||||
|
|
||||||
// VBO
|
|
||||||
// gl.glBindBuffer(GL2ES2.GL_ARRAY_BUFFER, 0); // You can unbind the VBO after it have been associated using glVertexAttribPointer
|
|
||||||
|
|
||||||
gl.glEnableVertexAttribArray(0);
|
|
||||||
|
|
||||||
// Select the VBO, GPU memory data, to use for colors
|
|
||||||
gl.glBindBuffer(GL2ES2.GL_ARRAY_BUFFER, vboHandles[COLOR_IDX]);
|
|
||||||
|
|
||||||
numBytes = numTriangles * 12 * 4;
|
|
||||||
gl.glBufferData(GL.GL_ARRAY_BUFFER, numBytes, fbColors, GL.GL_STATIC_DRAW);
|
|
||||||
|
|
||||||
// Associate Vertex attribute 1 with the last bound VBO
|
|
||||||
gl.glVertexAttribPointer(1 /* the color attribute */, 4 /* four possitions used for each vertex */,
|
|
||||||
GL2ES2.GL_FLOAT, false /* normalized? */, 0 /* stride */,
|
|
||||||
0 /* The bound VBO data offset */);
|
|
||||||
|
|
||||||
gl.glEnableVertexAttribArray(1);
|
|
||||||
|
|
||||||
// Select the VBO, GPU memory data, to use for texture
|
|
||||||
gl.glBindBuffer(GL2ES2.GL_ARRAY_BUFFER, vboHandles[TEXTURE_IDX]);
|
|
||||||
|
|
||||||
numBytes = numTriangles * 6 * 4;
|
|
||||||
gl.glBufferData(GL.GL_ARRAY_BUFFER, numBytes, fbTextureCoordinates, GL.GL_STATIC_DRAW);
|
|
||||||
|
|
||||||
// Associate Vertex attribute 1 with the last bound VBO
|
|
||||||
gl.glVertexAttribPointer(mTextureCoordinateHandle /* the texture attribute */, 2 /* two possitions used for each coordinate */,
|
|
||||||
GL2ES2.GL_FLOAT, false /* normalized? */, 0 /* stride */,
|
|
||||||
0 /* The bound VBO data offset */);
|
|
||||||
|
|
||||||
gl.glEnableVertexAttribArray(mTextureCoordinateHandle);
|
|
||||||
|
|
||||||
|
|
||||||
gl.glDrawArrays(GL2ES2.GL_TRIANGLES, 0, numTriangles*3); //Draw the vertices as triangle
|
|
||||||
|
|
||||||
gl.glDisableVertexAttribArray(0); // Allow release of vertex position memory
|
|
||||||
gl.glDisableVertexAttribArray(1); // Allow release of vertex color memory
|
|
||||||
gl.glDisableVertexAttribArray(mTextureCoordinateHandle); // Allow release of vertex texture memory
|
|
||||||
|
|
||||||
// disp.di
|
|
||||||
}
|
|
||||||
|
|
||||||
public void drawQuad() {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public void dispose(GLAutoDrawable drawable){
|
|
||||||
System.out.println("cleanup, remember to release shaders");
|
|
||||||
GL2ES2 gl = drawable.getGL().getGL2ES2();
|
|
||||||
gl.glUseProgram(0);
|
|
||||||
gl.glDeleteBuffers(3, vboHandles, 0); // Release VBO, color and vertices, buffer GPU memory.
|
|
||||||
vboHandles = null;
|
|
||||||
gl.glDetachShader(shaderProgram, vertShader);
|
|
||||||
gl.glDeleteShader(vertShader);
|
|
||||||
gl.glDetachShader(shaderProgram, fragShader);
|
|
||||||
gl.glDeleteShader(fragShader);
|
|
||||||
gl.glDeleteProgram(shaderProgram);
|
|
||||||
System.exit(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static Texture loadTexture(String file) throws GLException, IOException
|
|
||||||
{
|
|
||||||
ByteArrayOutputStream os = new ByteArrayOutputStream();
|
|
||||||
ImageIO.write(ImageIO.read(new File(file)), "png", os);
|
|
||||||
InputStream fis = new ByteArrayInputStream(os.toByteArray());
|
|
||||||
return TextureIO.newTexture(fis, true, TextureIO.PNG);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -0,0 +1,706 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) 2006-2016 Julien Gouesse 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; either version 2 of the
|
||||||
|
* License, or (at your option) any later version. This program 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,
|
||||||
|
* write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
|
||||||
|
* Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
package org.warp.picalculator.gui.graphicengine.gpu;
|
||||||
|
|
||||||
|
import java.lang.reflect.Field;
|
||||||
|
import java.lang.reflect.InvocationTargetException;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.nio.Buffer;
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
import java.nio.ByteOrder;
|
||||||
|
import java.nio.CharBuffer;
|
||||||
|
import java.nio.DoubleBuffer;
|
||||||
|
import java.nio.FloatBuffer;
|
||||||
|
import java.nio.IntBuffer;
|
||||||
|
import java.nio.LongBuffer;
|
||||||
|
import java.nio.ShortBuffer;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Map.Entry;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.logging.Level;
|
||||||
|
import java.util.logging.Logger;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper to deallocate memory on the native heap allocated during the creation
|
||||||
|
* of a direct byte buffer. It supports numerous virtual machines including
|
||||||
|
* OpenJDK, Oracle/Sun Java, Android Dalvik Virtual Machine, Apache Harmony and
|
||||||
|
* GNU Classpath. This class uses the syntax of Java 1.7 but it can work
|
||||||
|
* correctly with Java 1.4 with a very few minor type changes when using the
|
||||||
|
* maps and the collections. It relies on lots of implementation details but
|
||||||
|
* it's robust enough to go on working (except when the implementors
|
||||||
|
* intentionally use a very general class to store the buffers) despite minor
|
||||||
|
* naming changes like those that occurred between Java 1.6 and Java 1.7. It
|
||||||
|
* supports Java 1.9 despite the move of the cleaner from the package sun.misc
|
||||||
|
* to jdk.internal.ref (in the module java.base). N.B: Releasing the native
|
||||||
|
* memory of a sliced direct NIO buffer, the one of a direct NIO buffer created
|
||||||
|
* with JNI or the one of any direct NIO buffer created by the virtual machine
|
||||||
|
* or by a framework not under your control doesn't prevent the calls to methods
|
||||||
|
* attempting to access such buffers. Those calls can throw an exception or
|
||||||
|
* crash the virtual machine depending on the implementations.
|
||||||
|
*
|
||||||
|
* @author Julien Gouesse
|
||||||
|
*/
|
||||||
|
public class DeallocationHelper {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* tool responsible for releasing the native memory of a deallocatable byte
|
||||||
|
* buffer
|
||||||
|
*/
|
||||||
|
public static abstract class Deallocator {
|
||||||
|
|
||||||
|
public Deallocator() {
|
||||||
|
super();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* releases the native memory of a deallocatable byte buffer
|
||||||
|
*
|
||||||
|
* @param directByteBuffer
|
||||||
|
* deallocatable byte buffer
|
||||||
|
*
|
||||||
|
* @return <code>true</code> if the deallocation is successful,
|
||||||
|
* otherwise <code>false</code>
|
||||||
|
*/
|
||||||
|
public abstract boolean run(final ByteBuffer directByteBuffer);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class OracleSunOpenJdkDeallocator extends Deallocator {
|
||||||
|
|
||||||
|
private Method directByteBufferCleanerMethod;
|
||||||
|
|
||||||
|
private Method cleanerCleanMethod;
|
||||||
|
|
||||||
|
public OracleSunOpenJdkDeallocator() {
|
||||||
|
super();
|
||||||
|
try {
|
||||||
|
final Class<?> directByteBufferClass = Class.forName("java.nio.DirectByteBuffer");
|
||||||
|
directByteBufferCleanerMethod = directByteBufferClass.getDeclaredMethod("cleaner");
|
||||||
|
/**
|
||||||
|
* The return type is sun.misc.Cleaner in Java <= 1.8,
|
||||||
|
* jdk.internal.ref.Cleaner in Java >= 1.9. Only the latter
|
||||||
|
* implements the Runnable interface.
|
||||||
|
*/
|
||||||
|
final Class<?> cleanerClass = directByteBufferCleanerMethod.getReturnType();
|
||||||
|
if (Runnable.class.isAssignableFrom(cleanerClass)) {
|
||||||
|
cleanerCleanMethod = Runnable.class.getDeclaredMethod("run");
|
||||||
|
} else {
|
||||||
|
cleanerCleanMethod = cleanerClass.getDeclaredMethod("clean");
|
||||||
|
}
|
||||||
|
} catch (ClassNotFoundException | NoSuchMethodException e) {
|
||||||
|
logger.log(Level.WARNING, "The initialization of the deallocator for Oracle Java, Sun Java and OpenJDK has failed", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean run(final ByteBuffer directByteBuffer) {
|
||||||
|
boolean success = false;
|
||||||
|
if (directByteBufferCleanerMethod != null && cleanerCleanMethod != null) {
|
||||||
|
final boolean directByteBufferCleanerMethodWasAccessible = directByteBufferCleanerMethod.isAccessible();
|
||||||
|
final boolean cleanerCleanMethodWasAccessible = cleanerCleanMethod.isAccessible();
|
||||||
|
try {
|
||||||
|
// according to the Java documentation, by default, a reflected object is not accessible
|
||||||
|
directByteBufferCleanerMethod.setAccessible(true);
|
||||||
|
final Object cleaner = directByteBufferCleanerMethod.invoke(directByteBuffer);
|
||||||
|
if (cleaner != null) {
|
||||||
|
cleanerCleanMethod.setAccessible(true);
|
||||||
|
cleanerCleanMethod.invoke(cleaner);
|
||||||
|
success = true;
|
||||||
|
}
|
||||||
|
} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
|
||||||
|
logger.log(Level.WARNING, "The deallocation of a direct NIO buffer has failed", e);
|
||||||
|
} finally {
|
||||||
|
directByteBufferCleanerMethod.setAccessible(directByteBufferCleanerMethodWasAccessible);
|
||||||
|
cleanerCleanMethod.setAccessible(cleanerCleanMethodWasAccessible);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (success);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class AndroidDeallocator extends Deallocator {
|
||||||
|
|
||||||
|
private Method directByteBufferFreeMethod;
|
||||||
|
|
||||||
|
public AndroidDeallocator() {
|
||||||
|
super();
|
||||||
|
try {
|
||||||
|
final Class<?> directByteBufferClass = Class.forName("java.nio.DirectByteBuffer");
|
||||||
|
directByteBufferFreeMethod = directByteBufferClass.getDeclaredMethod("free");
|
||||||
|
} catch (ClassNotFoundException | NoSuchMethodException e) {
|
||||||
|
logger.log(Level.WARNING, "The initialization of the deallocator for Android has failed", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean run(final ByteBuffer directByteBuffer) {
|
||||||
|
boolean success = false;
|
||||||
|
if (directByteBufferFreeMethod != null) {
|
||||||
|
final boolean directByteBufferFreeMethodWasAccessible = directByteBufferFreeMethod.isAccessible();
|
||||||
|
try {
|
||||||
|
directByteBufferFreeMethod.setAccessible(true);
|
||||||
|
directByteBufferFreeMethod.invoke(directByteBuffer);
|
||||||
|
success = true;
|
||||||
|
} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
|
||||||
|
logger.log(Level.WARNING, "The deallocation of a direct NIO buffer has failed", e);
|
||||||
|
} finally {
|
||||||
|
directByteBufferFreeMethod.setAccessible(directByteBufferFreeMethodWasAccessible);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (success);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class GnuClasspathDeallocator extends Deallocator {
|
||||||
|
|
||||||
|
private Method vmDirectByteBufferFreeMethod;
|
||||||
|
|
||||||
|
private Field bufferAddressField;
|
||||||
|
|
||||||
|
public GnuClasspathDeallocator() {
|
||||||
|
super();
|
||||||
|
try {
|
||||||
|
final Class<?> vmDirectByteBufferClass = Class.forName("java.nio.VMDirectByteBuffer");
|
||||||
|
final Class<?> gnuClasspathPointerClass = Class.forName("gnu.classpath.Pointer");
|
||||||
|
vmDirectByteBufferFreeMethod = vmDirectByteBufferClass.getDeclaredMethod("free", gnuClasspathPointerClass);
|
||||||
|
bufferAddressField = Buffer.class.getDeclaredField("address");
|
||||||
|
} catch (ClassNotFoundException | NoSuchMethodException | NoSuchFieldException e) {
|
||||||
|
logger.log(Level.WARNING, "The initialization of the deallocator for GNU Classpath has failed", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean run(final ByteBuffer directByteBuffer) {
|
||||||
|
boolean success = false;
|
||||||
|
if (vmDirectByteBufferFreeMethod != null && bufferAddressField != null) {
|
||||||
|
final boolean bufferAddressFieldWasAccessible = bufferAddressField.isAccessible();
|
||||||
|
final boolean vmDirectByteBufferFreeMethodWasAccessible = vmDirectByteBufferFreeMethod.isAccessible();
|
||||||
|
try {
|
||||||
|
bufferAddressField.setAccessible(true);
|
||||||
|
final Object address = bufferAddressField.get(directByteBuffer);
|
||||||
|
if (address != null) {
|
||||||
|
vmDirectByteBufferFreeMethod.setAccessible(true);
|
||||||
|
vmDirectByteBufferFreeMethod.invoke(null, address);
|
||||||
|
success = true;
|
||||||
|
}
|
||||||
|
} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
|
||||||
|
logger.log(Level.WARNING, "The deallocation of a direct NIO buffer has failed", e);
|
||||||
|
} finally {
|
||||||
|
bufferAddressField.setAccessible(bufferAddressFieldWasAccessible);
|
||||||
|
vmDirectByteBufferFreeMethod.setAccessible(vmDirectByteBufferFreeMethodWasAccessible);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (success);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class ApacheHarmonyDeallocator extends Deallocator {
|
||||||
|
|
||||||
|
private Method directByteBufferFreeMethod;
|
||||||
|
|
||||||
|
public ApacheHarmonyDeallocator() {
|
||||||
|
super();
|
||||||
|
try {
|
||||||
|
final Class<?> directByteBufferClass = Class.forName("java.nio.DirectByteBuffer");
|
||||||
|
directByteBufferFreeMethod = directByteBufferClass.getDeclaredMethod("free");
|
||||||
|
} catch (ClassNotFoundException | NoSuchMethodException e) {
|
||||||
|
logger.log(Level.WARNING, "The initialization of the deallocator for Apache Harmony has failed", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean run(final ByteBuffer directByteBuffer) {
|
||||||
|
boolean success = false;
|
||||||
|
if (directByteBufferFreeMethod != null) {
|
||||||
|
final boolean directByteBufferFreeMethodWasAccessible = directByteBufferFreeMethod.isAccessible();
|
||||||
|
try {
|
||||||
|
directByteBufferFreeMethod.setAccessible(true);
|
||||||
|
directByteBufferFreeMethod.invoke(directByteBuffer);
|
||||||
|
success = true;
|
||||||
|
} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {
|
||||||
|
logger.log(Level.WARNING, "The deallocation of a direct NIO buffer has failed", e);
|
||||||
|
} finally {
|
||||||
|
directByteBufferFreeMethod.setAccessible(directByteBufferFreeMethodWasAccessible);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (success);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static final Logger logger = Logger.getLogger(DeallocationHelper.class.getName());
|
||||||
|
|
||||||
|
private Map<Class<?>, Field> attachmentOrByteBufferFieldMap;
|
||||||
|
|
||||||
|
private Set<Class<?>> deallocatableBufferClassSet;
|
||||||
|
|
||||||
|
private Deallocator deallocator;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Default constructor
|
||||||
|
*/
|
||||||
|
public DeallocationHelper() {
|
||||||
|
this(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Main constructor
|
||||||
|
*
|
||||||
|
* @param ignoreClassesAndFieldsHints
|
||||||
|
* <code>true</code> if the known implementation details should
|
||||||
|
* be ignored when looking for the classes and the fields used
|
||||||
|
* for the native memory of the direct buffers (they are then
|
||||||
|
* fully recomputed at runtime which is slower but safer),
|
||||||
|
* otherwise <code>false</code>
|
||||||
|
*/
|
||||||
|
public DeallocationHelper(final boolean ignoreClassesAndFieldsHints) {
|
||||||
|
super();
|
||||||
|
final List<Buffer> buffersToDelete = new ArrayList<>();
|
||||||
|
/**
|
||||||
|
* builds the map used to determine the names of the fields containing
|
||||||
|
* the direct byte buffers. The direct read only buffers and the sliced
|
||||||
|
* buffers and the direct buffers for other primitive types than bytes
|
||||||
|
* store their data into some direct byte buffers. Those direct byte
|
||||||
|
* buffers often are the only one accessing directly to the native
|
||||||
|
* memory. That's why it's necessary to find them when a developer
|
||||||
|
* passes a direct NIO buffer. The code below relies on numerous
|
||||||
|
* implementation details found in some classes not available in the
|
||||||
|
* public APIs, it's used to find the fields faster in most of the
|
||||||
|
* cases. The class names haven't changed since Java 1.4 unlike a few
|
||||||
|
* field names.
|
||||||
|
*/
|
||||||
|
final Map<String, String> attachmentOrByteBufferFieldNameMap = new HashMap<>();
|
||||||
|
final String javaVendor = System.getProperty("java.vendor");
|
||||||
|
final String javaVersion = System.getProperty("java.version");
|
||||||
|
if (!ignoreClassesAndFieldsHints) {
|
||||||
|
if (javaVendor.equals("Sun Microsystems Inc.") || javaVendor.equals("Oracle Corporation")) {
|
||||||
|
final String java14to16DirectBufferAttachmentFieldName = "viewedBuffer";
|
||||||
|
final String java17to19DirectBufferAttachmentFieldName = "att";
|
||||||
|
final String byteBufferAsNonByteBufferByteBufferFieldName = "bb";
|
||||||
|
final String[] directBufferClassnames = new String[] { "java.nio.DirectByteBuffer", "java.nio.DirectByteBufferR", "java.nio.DirectCharBufferRS", "java.nio.DirectCharBufferRU", "java.nio.DirectCharBufferS", "java.nio.DirectCharBufferU", "java.nio.DirectDoubleBufferRS", "java.nio.DirectDoubleBufferRU", "java.nio.DirectDoubleBufferS", "java.nio.DirectDoubleBufferU", "java.nio.DirectFloatBufferRS", "java.nio.DirectFloatBufferRU", "java.nio.DirectFloatBufferS", "java.nio.DirectFloatBufferU", "java.nio.DirectIntBufferRS", "java.nio.DirectIntBufferRU", "java.nio.DirectIntBufferS", "java.nio.DirectIntBufferU", "java.nio.DirectLongBufferRS", "java.nio.DirectLongBufferRU", "java.nio.DirectLongBufferS", "java.nio.DirectLongBufferU", "java.nio.DirectShortBufferRS", "java.nio.DirectShortBufferRU", "java.nio.DirectShortBufferS", "java.nio.DirectShortBufferU" };
|
||||||
|
final String[] byteBufferAsNonByteBufferClassnames = new String[] { "java.nio.ByteBufferAsCharBufferB", "java.nio.ByteBufferAsCharBufferL", "java.nio.ByteBufferAsCharBufferRB", "java.nio.ByteBufferAsCharBufferRL", "java.nio.ByteBufferAsDoubleBufferB", "java.nio.ByteBufferAsDoubleBufferL", "java.nio.ByteBufferAsDoubleBufferRB", "java.nio.ByteBufferAsDoubleBufferRL", "java.nio.ByteBufferAsFloatBufferB", "java.nio.ByteBufferAsFloatBufferL", "java.nio.ByteBufferAsFloatBufferRB", "java.nio.ByteBufferAsFloatBufferRL", "java.nio.ByteBufferAsIntBufferB", "java.nio.ByteBufferAsIntBufferL", "java.nio.ByteBufferAsIntBufferRB", "java.nio.ByteBufferAsIntBufferRL", "java.nio.ByteBufferAsLongBufferB", "java.nio.ByteBufferAsLongBufferL", "java.nio.ByteBufferAsLongBufferRB", "java.nio.ByteBufferAsLongBufferRL", "java.nio.ByteBufferAsShortBufferB", "java.nio.ByteBufferAsShortBufferL", "java.nio.ByteBufferAsShortBufferRB", "java.nio.ByteBufferAsShortBufferRL" };
|
||||||
|
final String[] javaVersionElements = System.getProperty("java.version").split("\\.");
|
||||||
|
final int indexOfEarlyAccessSuffix = javaVersionElements[0].lastIndexOf("-ea");
|
||||||
|
if (indexOfEarlyAccessSuffix != -1) {
|
||||||
|
// drops the "-ea" suffix from the major version number for
|
||||||
|
// an early access build
|
||||||
|
javaVersionElements[0] = javaVersionElements[0].substring(0, indexOfEarlyAccessSuffix);
|
||||||
|
}
|
||||||
|
final int major, minor;
|
||||||
|
if (javaVersionElements.length >= 2) {
|
||||||
|
major = Integer.parseInt(javaVersionElements[0]);
|
||||||
|
minor = Integer.parseInt(javaVersionElements[1]);
|
||||||
|
} else {
|
||||||
|
major = 1;
|
||||||
|
minor = Integer.parseInt(javaVersionElements[0]);
|
||||||
|
}
|
||||||
|
final String directBufferAttachmentFieldName;
|
||||||
|
if (minor == 1 && major <= 6) {
|
||||||
|
directBufferAttachmentFieldName = java14to16DirectBufferAttachmentFieldName;
|
||||||
|
} else {
|
||||||
|
directBufferAttachmentFieldName = java17to19DirectBufferAttachmentFieldName;
|
||||||
|
}
|
||||||
|
for (final String directBufferClassname : directBufferClassnames) {
|
||||||
|
attachmentOrByteBufferFieldNameMap.put(directBufferClassname, directBufferAttachmentFieldName);
|
||||||
|
}
|
||||||
|
for (final String byteBufferAsNonByteBufferClassname : byteBufferAsNonByteBufferClassnames) {
|
||||||
|
attachmentOrByteBufferFieldNameMap.put(byteBufferAsNonByteBufferClassname, byteBufferAsNonByteBufferByteBufferFieldName);
|
||||||
|
}
|
||||||
|
} else if (javaVendor.equals("The Android Project")) {
|
||||||
|
final String byteBufferAsNonByteBufferByteBufferFieldName = "byteBuffer";
|
||||||
|
final String[] byteBufferAsNonByteBufferClassnames = new String[] { "java.nio.ByteBufferAsCharBuffer", "java.nio.ByteBufferAsDoubleBuffer", "java.nio.ByteBufferAsFloatBuffer", "java.nio.ByteBufferAsIntBuffer", "java.nio.ByteBufferAsLongBuffer", "java.nio.ByteBufferAsShortBuffer" };
|
||||||
|
for (final String byteBufferAsNonByteBufferClassname : byteBufferAsNonByteBufferClassnames) {
|
||||||
|
attachmentOrByteBufferFieldNameMap.put(byteBufferAsNonByteBufferClassname, byteBufferAsNonByteBufferByteBufferFieldName);
|
||||||
|
}
|
||||||
|
} else if (/* javaVendor.equals("Apple Inc.")|| */javaVendor.equals("Free Software Foundation, Inc.")) {
|
||||||
|
final String byteBufferAsNonByteBufferByteBufferFieldName = "bb";
|
||||||
|
final String[] byteBufferAsNonByteBufferClassnames = new String[] { "java.nio.CharViewBufferImpl", "java.nio.DoubleViewBufferImpl", "java.nio.FloatViewBufferImpl", "java.nio.IntViewBufferImpl", "java.nio.LongViewBufferImpl", "java.nio.ShortViewBufferImpl" };
|
||||||
|
for (final String byteBufferAsNonByteBufferClassname : byteBufferAsNonByteBufferClassnames) {
|
||||||
|
attachmentOrByteBufferFieldNameMap.put(byteBufferAsNonByteBufferClassname, byteBufferAsNonByteBufferByteBufferFieldName);
|
||||||
|
}
|
||||||
|
} else if (javaVendor.contains("Apache")) {
|
||||||
|
final String byteBufferAsNonByteBufferByteBufferFieldName = "byteBuffer";
|
||||||
|
final String[] byteBufferAsNonByteBufferClassnames = new String[] { "java.nio.CharToByteBufferAdapter", "java.nio.DoubleToByteBufferAdapter", "java.nio.FloatToByteBufferAdapter", "java.nio.IntToByteBufferAdapter", "java.nio.LongToByteBufferAdapter", "java.nio.ShortToByteBufferAdapter" };
|
||||||
|
for (final String byteBufferAsNonByteBufferClassname : byteBufferAsNonByteBufferClassnames) {
|
||||||
|
attachmentOrByteBufferFieldNameMap.put(byteBufferAsNonByteBufferClassname, byteBufferAsNonByteBufferByteBufferFieldName);
|
||||||
|
}
|
||||||
|
} else if (javaVendor.equals("Jeroen Frijters")) {// TODO IKVM
|
||||||
|
} else if (javaVendor.contains("IBM")) {// TODO J9
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// checks if these classes are in the class library
|
||||||
|
if (!attachmentOrByteBufferFieldNameMap.isEmpty()) {
|
||||||
|
final List<String> classnamesToRemove = new ArrayList<>();
|
||||||
|
for (final String classname : attachmentOrByteBufferFieldNameMap.keySet()) {
|
||||||
|
try {
|
||||||
|
Class.forName(classname);
|
||||||
|
} catch (final ClassNotFoundException cnfe) {
|
||||||
|
classnamesToRemove.add(classname);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (final String classnameToRemove : classnamesToRemove) {
|
||||||
|
attachmentOrByteBufferFieldNameMap.remove(classnameToRemove);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// builds the map used to determine the fields containing the direct
|
||||||
|
// byte buffers
|
||||||
|
attachmentOrByteBufferFieldMap = new HashMap<>();
|
||||||
|
if (!attachmentOrByteBufferFieldNameMap.isEmpty()) {
|
||||||
|
for (final Entry<String, String> attachmentOrByteBufferFieldNameEntry : attachmentOrByteBufferFieldNameMap.entrySet()) {
|
||||||
|
final String classname = attachmentOrByteBufferFieldNameEntry.getKey();
|
||||||
|
final String fieldname = attachmentOrByteBufferFieldNameEntry.getValue();
|
||||||
|
try {
|
||||||
|
final Class<?> bufferClass = Class.forName(classname);
|
||||||
|
Field bufferField = null;
|
||||||
|
Class<?> bufferIntermediaryClass = bufferClass;
|
||||||
|
final List<Class<?>> intermediaryClassWithoutBufferList = new ArrayList<>();
|
||||||
|
while (bufferIntermediaryClass != null) {
|
||||||
|
try {
|
||||||
|
bufferField = bufferIntermediaryClass.getDeclaredField(fieldname);
|
||||||
|
} catch (final NoSuchFieldException nsfe) {
|
||||||
|
if (!bufferIntermediaryClass.equals(Object.class) && !bufferIntermediaryClass.equals(Buffer.class)) {
|
||||||
|
intermediaryClassWithoutBufferList.add(bufferIntermediaryClass);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
bufferIntermediaryClass = bufferIntermediaryClass.getSuperclass();
|
||||||
|
}
|
||||||
|
if (bufferField == null) {
|
||||||
|
final String superClassesMsg;
|
||||||
|
if (intermediaryClassWithoutBufferList.isEmpty()) {
|
||||||
|
superClassesMsg = "";
|
||||||
|
} else if (intermediaryClassWithoutBufferList.size() == 1) {
|
||||||
|
superClassesMsg = " and in its super class " + intermediaryClassWithoutBufferList.get(0).getName();
|
||||||
|
} else {
|
||||||
|
final StringBuilder builder = new StringBuilder();
|
||||||
|
builder.append(" and in its super classes");
|
||||||
|
int classIndex = 0;
|
||||||
|
for (final Class<?> intermediaryClassWithoutBuffer : intermediaryClassWithoutBufferList) {
|
||||||
|
builder.append(' ');
|
||||||
|
builder.append(intermediaryClassWithoutBuffer.getName());
|
||||||
|
if (classIndex < intermediaryClassWithoutBufferList.size() - 1) {
|
||||||
|
builder.append(',');
|
||||||
|
}
|
||||||
|
classIndex++;
|
||||||
|
}
|
||||||
|
superClassesMsg = builder.toString();
|
||||||
|
}
|
||||||
|
logger.warning("The field " + fieldname + " hasn't been found in the class " + classname + superClassesMsg);
|
||||||
|
} else {// the field has been found, stores it into the map
|
||||||
|
attachmentOrByteBufferFieldMap.put(bufferClass, bufferField);
|
||||||
|
}
|
||||||
|
} catch (final ClassNotFoundException cnfe) {// TODO The Java version
|
||||||
|
// isn't very useful
|
||||||
|
// under
|
||||||
|
// Android as it is
|
||||||
|
// always zero, rather
|
||||||
|
// use
|
||||||
|
// android.os.Build.VERSION.RELEASE
|
||||||
|
// to show something
|
||||||
|
// meaningful supported
|
||||||
|
// since the API level 1
|
||||||
|
final String msg = "The class " + classname + " hasn't been found while initializing the deallocator. Java vendor: " + javaVendor + " Java version: " + javaVersion;
|
||||||
|
logger.log(Level.WARNING, msg, cnfe);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// if a known implementation has drastically changed or if the current
|
||||||
|
// implementation is unknown
|
||||||
|
if (attachmentOrByteBufferFieldNameMap.isEmpty()) {// detects everything
|
||||||
|
// with the
|
||||||
|
// reflection API
|
||||||
|
// creates all
|
||||||
|
// possible kinds of
|
||||||
|
// direct NIO buffer
|
||||||
|
// that can contain
|
||||||
|
// buffers (sliced
|
||||||
|
// buffers and views)
|
||||||
|
final ByteBuffer slicedBigEndianReadOnlyDirectByteBuffer = ((ByteBuffer) ByteBuffer.allocateDirect(2).order(ByteOrder.BIG_ENDIAN).put((byte) 0).put((byte) 0).position(1).limit(2)).slice().asReadOnlyBuffer();
|
||||||
|
final ByteBuffer slicedBigEndianReadWriteDirectByteBuffer = ((ByteBuffer) ByteBuffer.allocateDirect(2).order(ByteOrder.BIG_ENDIAN).put((byte) 0).put((byte) 0).position(1).limit(2)).slice();
|
||||||
|
final CharBuffer bigEndianReadOnlyDirectCharBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asReadOnlyBuffer().asCharBuffer();
|
||||||
|
final CharBuffer bigEndianReadWriteDirectCharBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asCharBuffer();
|
||||||
|
final DoubleBuffer bigEndianReadOnlyDirectDoubleBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asReadOnlyBuffer().asDoubleBuffer();
|
||||||
|
final DoubleBuffer bigEndianReadWriteDirectDoubleBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asDoubleBuffer();
|
||||||
|
final FloatBuffer bigEndianReadOnlyDirectFloatBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asReadOnlyBuffer().asFloatBuffer();
|
||||||
|
final FloatBuffer bigEndianReadWriteDirectFloatBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asFloatBuffer();
|
||||||
|
final IntBuffer bigEndianReadOnlyDirectIntBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asReadOnlyBuffer().asIntBuffer();
|
||||||
|
final IntBuffer bigEndianReadWriteDirectIntBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asIntBuffer();
|
||||||
|
final LongBuffer bigEndianReadOnlyDirectLongBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asReadOnlyBuffer().asLongBuffer();
|
||||||
|
final LongBuffer bigEndianReadWriteDirectLongBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asLongBuffer();
|
||||||
|
final ShortBuffer bigEndianReadOnlyDirectShortBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asReadOnlyBuffer().asShortBuffer();
|
||||||
|
final ShortBuffer bigEndianReadWriteDirectShortBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.BIG_ENDIAN).asShortBuffer();
|
||||||
|
final ByteBuffer slicedLittleEndianReadOnlyDirectByteBuffer = ((ByteBuffer) ByteBuffer.allocateDirect(2).order(ByteOrder.LITTLE_ENDIAN).put((byte) 0).put((byte) 0).position(1).limit(2)).slice().asReadOnlyBuffer();
|
||||||
|
final ByteBuffer slicedLittleEndianReadWriteDirectByteBuffer = ((ByteBuffer) ByteBuffer.allocateDirect(2).order(ByteOrder.LITTLE_ENDIAN).put((byte) 0).put((byte) 0).position(1).limit(2)).slice();
|
||||||
|
final CharBuffer littleEndianReadOnlyDirectCharBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asReadOnlyBuffer().asCharBuffer();
|
||||||
|
final CharBuffer littleEndianReadWriteDirectCharBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asCharBuffer();
|
||||||
|
final DoubleBuffer littleEndianReadOnlyDirectDoubleBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asReadOnlyBuffer().asDoubleBuffer();
|
||||||
|
final DoubleBuffer littleEndianReadWriteDirectDoubleBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asDoubleBuffer();
|
||||||
|
final FloatBuffer littleEndianReadOnlyDirectFloatBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asReadOnlyBuffer().asFloatBuffer();
|
||||||
|
final FloatBuffer littleEndianReadWriteDirectFloatBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asFloatBuffer();
|
||||||
|
final IntBuffer littleEndianReadOnlyDirectIntBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asReadOnlyBuffer().asIntBuffer();
|
||||||
|
final IntBuffer littleEndianReadWriteDirectIntBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asIntBuffer();
|
||||||
|
final LongBuffer littleEndianReadOnlyDirectLongBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asReadOnlyBuffer().asLongBuffer();
|
||||||
|
final LongBuffer littleEndianReadWriteDirectLongBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asLongBuffer();
|
||||||
|
final ShortBuffer littleEndianReadOnlyDirectShortBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asReadOnlyBuffer().asShortBuffer();
|
||||||
|
final ShortBuffer littleEndianReadWriteDirectShortBuffer = ByteBuffer.allocateDirect(1).order(ByteOrder.LITTLE_ENDIAN).asShortBuffer();
|
||||||
|
final List<Buffer> buffers = new ArrayList<>();
|
||||||
|
buffers.add(slicedBigEndianReadOnlyDirectByteBuffer);
|
||||||
|
buffers.add(slicedBigEndianReadWriteDirectByteBuffer);
|
||||||
|
buffers.add(bigEndianReadOnlyDirectCharBuffer);
|
||||||
|
buffers.add(bigEndianReadWriteDirectCharBuffer);
|
||||||
|
buffers.add(bigEndianReadOnlyDirectDoubleBuffer);
|
||||||
|
buffers.add(bigEndianReadWriteDirectDoubleBuffer);
|
||||||
|
buffers.add(bigEndianReadOnlyDirectFloatBuffer);
|
||||||
|
buffers.add(bigEndianReadWriteDirectFloatBuffer);
|
||||||
|
buffers.add(bigEndianReadOnlyDirectIntBuffer);
|
||||||
|
buffers.add(bigEndianReadWriteDirectIntBuffer);
|
||||||
|
buffers.add(bigEndianReadOnlyDirectLongBuffer);
|
||||||
|
buffers.add(bigEndianReadWriteDirectLongBuffer);
|
||||||
|
buffers.add(bigEndianReadOnlyDirectShortBuffer);
|
||||||
|
buffers.add(bigEndianReadWriteDirectShortBuffer);
|
||||||
|
buffers.add(slicedLittleEndianReadOnlyDirectByteBuffer);
|
||||||
|
buffers.add(slicedLittleEndianReadWriteDirectByteBuffer);
|
||||||
|
buffers.add(littleEndianReadOnlyDirectCharBuffer);
|
||||||
|
buffers.add(littleEndianReadWriteDirectCharBuffer);
|
||||||
|
buffers.add(littleEndianReadOnlyDirectDoubleBuffer);
|
||||||
|
buffers.add(littleEndianReadWriteDirectDoubleBuffer);
|
||||||
|
buffers.add(littleEndianReadOnlyDirectFloatBuffer);
|
||||||
|
buffers.add(littleEndianReadWriteDirectFloatBuffer);
|
||||||
|
buffers.add(littleEndianReadOnlyDirectIntBuffer);
|
||||||
|
buffers.add(littleEndianReadWriteDirectIntBuffer);
|
||||||
|
buffers.add(littleEndianReadOnlyDirectLongBuffer);
|
||||||
|
buffers.add(littleEndianReadWriteDirectLongBuffer);
|
||||||
|
buffers.add(littleEndianReadOnlyDirectShortBuffer);
|
||||||
|
buffers.add(littleEndianReadWriteDirectShortBuffer);
|
||||||
|
// gets the fields to access the contained buffers
|
||||||
|
for (final Buffer buffer : buffers) {
|
||||||
|
final Class<?> bufferClass = buffer.getClass();
|
||||||
|
if (!attachmentOrByteBufferFieldMap.containsKey(bufferClass)) {
|
||||||
|
Field bufferField = null;
|
||||||
|
Class<?> bufferIntermediaryClass = bufferClass;
|
||||||
|
while (bufferIntermediaryClass != null && bufferField == null) {
|
||||||
|
for (final Field field : bufferIntermediaryClass.getDeclaredFields()) {
|
||||||
|
final boolean fieldWasAccessible = field.isAccessible();
|
||||||
|
try {
|
||||||
|
field.setAccessible(true);
|
||||||
|
final Object fieldValue = field.get(buffer);
|
||||||
|
if (fieldValue != null && fieldValue instanceof Buffer) {
|
||||||
|
bufferField = field;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} catch (final IllegalAccessException iae) {
|
||||||
|
logger.log(Level.WARNING, "Cannot access the field " + field.getName() + " of the class " + bufferIntermediaryClass.getName(), iae);
|
||||||
|
} finally {
|
||||||
|
field.setAccessible(fieldWasAccessible);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
bufferIntermediaryClass = bufferIntermediaryClass.getSuperclass();
|
||||||
|
}
|
||||||
|
if (bufferField != null) {
|
||||||
|
attachmentOrByteBufferFieldMap.put(bufferClass, bufferField);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// cleans the mess
|
||||||
|
buffersToDelete.addAll(buffers);
|
||||||
|
}
|
||||||
|
// builds the set of classes whose instances can be deallocated
|
||||||
|
deallocatableBufferClassSet = new HashSet<>();
|
||||||
|
if (javaVendor.equals("Sun Microsystems Inc.") || javaVendor.equals("Oracle Corporation") || javaVendor.equals("The Android Project")) {
|
||||||
|
Class<?> directByteBufferClass = null;
|
||||||
|
final String directByteBufferClassName = "java.nio.DirectByteBuffer";
|
||||||
|
try {
|
||||||
|
directByteBufferClass = Class.forName(directByteBufferClassName);
|
||||||
|
} catch (final ClassNotFoundException cnfe) {
|
||||||
|
final String msg = "The class " + directByteBufferClassName + " hasn't been found while initializing the deallocator. Java vendor: " + javaVendor + " Java version: " + javaVersion;
|
||||||
|
logger.log(Level.WARNING, msg, cnfe);
|
||||||
|
}
|
||||||
|
if (directByteBufferClass != null) {
|
||||||
|
deallocatableBufferClassSet.add(directByteBufferClass);
|
||||||
|
}
|
||||||
|
} else if (/* javaVendor.equals("Apple Inc.")|| */javaVendor.equals("Free Software Foundation, Inc.")) {
|
||||||
|
Class<?> readOnlyDirectByteBufferClass = null;
|
||||||
|
final String readOnlyDirectByteBufferClassName = "java.nio.DirectByteBufferImpl.ReadOnly";
|
||||||
|
try {
|
||||||
|
readOnlyDirectByteBufferClass = Class.forName(readOnlyDirectByteBufferClassName);
|
||||||
|
} catch (final ClassNotFoundException cnfe) {
|
||||||
|
final String msg = "The class " + readOnlyDirectByteBufferClassName + " hasn't been found while initializing the deallocator. Java vendor: " + javaVendor + " Java version: " + javaVersion;
|
||||||
|
logger.log(Level.WARNING, msg, cnfe);
|
||||||
|
}
|
||||||
|
if (readOnlyDirectByteBufferClass != null) {
|
||||||
|
deallocatableBufferClassSet.add(readOnlyDirectByteBufferClass);
|
||||||
|
}
|
||||||
|
Class<?> readWriteDirectByteBufferClass = null;
|
||||||
|
final String readWriteDirectByteBufferClassName = "java.nio.DirectByteBufferImpl.ReadWrite";
|
||||||
|
try {
|
||||||
|
readWriteDirectByteBufferClass = Class.forName(readWriteDirectByteBufferClassName);
|
||||||
|
} catch (final ClassNotFoundException cnfe) {
|
||||||
|
final String msg = "The class " + readWriteDirectByteBufferClassName + " hasn't been found while initializing the deallocator. Java vendor: " + javaVendor + " Java version: " + javaVersion;
|
||||||
|
logger.log(Level.WARNING, msg, cnfe);
|
||||||
|
}
|
||||||
|
if (readWriteDirectByteBufferClass != null) {
|
||||||
|
deallocatableBufferClassSet.add(readWriteDirectByteBufferClass);
|
||||||
|
}
|
||||||
|
} else if (javaVendor.contains("Apache")) {
|
||||||
|
Class<?> readOnlyDirectByteBufferClass = null;
|
||||||
|
final String readOnlyDirectByteBufferClassName = "java.nio.ReadOnlyDirectByteBuffer";
|
||||||
|
try {
|
||||||
|
readOnlyDirectByteBufferClass = Class.forName(readOnlyDirectByteBufferClassName);
|
||||||
|
} catch (final ClassNotFoundException cnfe) {
|
||||||
|
final String msg = "The class " + readOnlyDirectByteBufferClassName + " hasn't been found while initializing the deallocator. Java vendor: " + javaVendor + " Java version: " + javaVersion;
|
||||||
|
logger.log(Level.WARNING, msg, cnfe);
|
||||||
|
}
|
||||||
|
if (readOnlyDirectByteBufferClass != null) {
|
||||||
|
deallocatableBufferClassSet.add(readOnlyDirectByteBufferClass);
|
||||||
|
}
|
||||||
|
Class<?> readWriteDirectByteBufferClass = null;
|
||||||
|
final String readWriteDirectByteBufferClassName = "java.nio.ReadWriteDirectByteBuffer";
|
||||||
|
try {
|
||||||
|
readWriteDirectByteBufferClass = Class.forName(readWriteDirectByteBufferClassName);
|
||||||
|
} catch (final ClassNotFoundException cnfe) {
|
||||||
|
final String msg = "The class " + readWriteDirectByteBufferClassName + " hasn't been found while initializing the deallocator. Java vendor: " + javaVendor + " Java version: " + javaVersion;
|
||||||
|
logger.log(Level.WARNING, msg, cnfe);
|
||||||
|
}
|
||||||
|
if (readWriteDirectByteBufferClass != null) {
|
||||||
|
deallocatableBufferClassSet.add(readWriteDirectByteBufferClass);
|
||||||
|
}
|
||||||
|
} else if (javaVendor.equals("Jeroen Frijters")) {// TODO IKVM
|
||||||
|
} else if (javaVendor.contains("IBM")) {// TODO J9
|
||||||
|
}
|
||||||
|
// if there is no known implementation class of the direct byte buffers
|
||||||
|
if (deallocatableBufferClassSet.isEmpty()) {// creates a read write
|
||||||
|
// direct byte buffer
|
||||||
|
final ByteBuffer dummyReadWriteDirectByteBuffer = ByteBuffer.allocateDirect(1);
|
||||||
|
// gets its class
|
||||||
|
final Class<?> readWriteDirectByteBufferClass = dummyReadWriteDirectByteBuffer.getClass();
|
||||||
|
// stores this class
|
||||||
|
deallocatableBufferClassSet.add(readWriteDirectByteBufferClass);
|
||||||
|
// cleans the mess
|
||||||
|
buffersToDelete.add(dummyReadWriteDirectByteBuffer);
|
||||||
|
// creates a read only direct byte buffer
|
||||||
|
final ByteBuffer dummyReadOnlyDirectByteBuffer = ByteBuffer.allocateDirect(1).asReadOnlyBuffer();
|
||||||
|
// gets its class
|
||||||
|
final Class<?> readOnlyDirectByteBufferClass = dummyReadOnlyDirectByteBuffer.getClass();
|
||||||
|
// stores this class
|
||||||
|
deallocatableBufferClassSet.add(readOnlyDirectByteBufferClass);
|
||||||
|
// cleans the mess
|
||||||
|
buffersToDelete.add(dummyReadOnlyDirectByteBuffer);
|
||||||
|
}
|
||||||
|
// builds the deallocator responsible for releasing the native memory of
|
||||||
|
// a deallocatable byte buffer
|
||||||
|
if (javaVendor.equals("Sun Microsystems Inc.") || javaVendor.equals("Oracle Corporation")) {
|
||||||
|
deallocator = new OracleSunOpenJdkDeallocator();
|
||||||
|
} else if (javaVendor.equals("The Android Project")) {
|
||||||
|
deallocator = new AndroidDeallocator();
|
||||||
|
} else if (/* javaVendor.equals("Apple Inc.")|| */javaVendor.equals("Free Software Foundation, Inc.")) {
|
||||||
|
deallocator = new GnuClasspathDeallocator();
|
||||||
|
} else if (javaVendor.contains("Apache")) {
|
||||||
|
deallocator = new ApacheHarmonyDeallocator();
|
||||||
|
} else if (javaVendor.equals("Jeroen Frijters")) {// TODO IKVM
|
||||||
|
deallocator = null;
|
||||||
|
} else if (javaVendor.contains("IBM")) {// TODO J9
|
||||||
|
deallocator = null;
|
||||||
|
} else {
|
||||||
|
deallocator = null;
|
||||||
|
}
|
||||||
|
// final cleanup
|
||||||
|
for (final Buffer bufferToDelete : buffersToDelete) {
|
||||||
|
deallocate(bufferToDelete);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public ByteBuffer findDeallocatableBuffer(Buffer buffer) {
|
||||||
|
final ByteBuffer deallocatableDirectByteBuffer;
|
||||||
|
// looks only for the direct buffers
|
||||||
|
if (buffer != null && buffer.isDirect()) {// looks for any contained
|
||||||
|
// buffer in the passed buffer
|
||||||
|
final Class<?> bufferClass = buffer.getClass();
|
||||||
|
final Field attachmentOrByteBufferField = attachmentOrByteBufferFieldMap == null ? null : attachmentOrByteBufferFieldMap.get(bufferClass);
|
||||||
|
final Buffer attachmentBufferOrByteBuffer;
|
||||||
|
if (attachmentOrByteBufferField == null) {
|
||||||
|
attachmentBufferOrByteBuffer = null;
|
||||||
|
} else {
|
||||||
|
Object attachedObjectOrByteBuffer;
|
||||||
|
final boolean attachedObjectOrByteBufferFieldWasAccessible = attachmentOrByteBufferField.isAccessible();
|
||||||
|
try {
|
||||||
|
attachmentOrByteBufferField.setAccessible(true);
|
||||||
|
attachedObjectOrByteBuffer = attachmentOrByteBufferField.get(buffer);
|
||||||
|
} catch (IllegalArgumentException | IllegalAccessException iae) {
|
||||||
|
attachedObjectOrByteBuffer = null;
|
||||||
|
} finally {
|
||||||
|
attachmentOrByteBufferField.setAccessible(attachedObjectOrByteBufferFieldWasAccessible);
|
||||||
|
}
|
||||||
|
if (attachedObjectOrByteBuffer instanceof Buffer) {
|
||||||
|
attachmentBufferOrByteBuffer = (Buffer) attachedObjectOrByteBuffer;
|
||||||
|
} else {
|
||||||
|
attachmentBufferOrByteBuffer = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// if there is no buffer inside the buffer given in input
|
||||||
|
if (attachmentBufferOrByteBuffer == null) {// if it's a direct byte
|
||||||
|
// buffer and if it's an
|
||||||
|
// instance of
|
||||||
|
// a deallocatable buffer
|
||||||
|
// class
|
||||||
|
if (buffer instanceof ByteBuffer && deallocatableBufferClassSet.contains(bufferClass)) {
|
||||||
|
deallocatableDirectByteBuffer = (ByteBuffer) buffer;
|
||||||
|
} else {// it's not a byte buffer or it's not a
|
||||||
|
// deallocatable buffer
|
||||||
|
deallocatableDirectByteBuffer = null;
|
||||||
|
final String bufferClassName = bufferClass.getName();
|
||||||
|
logger.warning("No deallocatable buffer has been found for an instance of the class " + bufferClassName + " whereas it is a direct NIO buffer");
|
||||||
|
}
|
||||||
|
} else {// the passed buffer contains another buffer, looks for a
|
||||||
|
// deallocatable buffer inside it
|
||||||
|
deallocatableDirectByteBuffer = findDeallocatableBuffer(attachmentBufferOrByteBuffer);
|
||||||
|
}
|
||||||
|
} else {// there is no need to clean the heap based buffers
|
||||||
|
deallocatableDirectByteBuffer = null;
|
||||||
|
}
|
||||||
|
return deallocatableDirectByteBuffer;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void deallocate(final Buffer buffer) {
|
||||||
|
if (deallocator != null) {
|
||||||
|
final ByteBuffer deallocatableBuffer = findDeallocatableBuffer(buffer);
|
||||||
|
if (deallocatableBuffer != null) {
|
||||||
|
deallocator.run(deallocatableBuffer);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public Deallocator getDeallocator() {
|
||||||
|
return (deallocator);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDeallocator(Deallocator deallocator) {
|
||||||
|
this.deallocator = deallocator;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Map<Class<?>, Field> getAttachmentOrByteBufferFieldMap() {
|
||||||
|
return (attachmentOrByteBufferFieldMap);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setAttachmentOrByteBufferFieldMap(Map<Class<?>, Field> attachmentOrByteBufferFieldMap) {
|
||||||
|
this.attachmentOrByteBufferFieldMap = attachmentOrByteBufferFieldMap;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Set<Class<?>> getDeallocatableBufferClassSet() {
|
||||||
|
return (deallocatableBufferClassSet);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void setDeallocatableBufferClassSet(Set<Class<?>> deallocatableBufferClassSet) {
|
||||||
|
this.deallocatableBufferClassSet = deallocatableBufferClassSet;
|
||||||
|
}
|
||||||
|
}
|
@ -1,23 +1,28 @@
|
|||||||
package org.warp.picalculator.gui.graphicengine.gpu;
|
package org.warp.picalculator.gui.graphicengine.gpu;
|
||||||
|
|
||||||
import java.awt.image.BufferedImage;
|
import java.io.IOException;
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.graphicengine.Drawable;
|
import org.warp.picalculator.gui.graphicengine.Drawable;
|
||||||
import org.warp.picalculator.gui.graphicengine.Renderer;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
|
|
||||||
|
import com.jogamp.opengl.GLProfile;
|
||||||
|
import com.jogamp.opengl.egl.EGL;
|
||||||
|
|
||||||
public class GPUDisplay implements org.warp.picalculator.gui.graphicengine.Display {
|
public class GPUDisplay implements org.warp.picalculator.gui.graphicengine.Display {
|
||||||
|
|
||||||
private boolean initialized = false;
|
private volatile boolean initialized = false;
|
||||||
private CalculatorWindow wnd;
|
private volatile boolean created = false;
|
||||||
|
private NEWTWindow wnd;
|
||||||
private Drawable d;
|
private Drawable d;
|
||||||
private GPURenderer r;
|
private GPURenderer r;
|
||||||
|
int[] size = new int[]{Main.screenSize[0], Main.screenSize[1]};
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int[] getSize() {
|
public int[] getSize() {
|
||||||
// TODO Auto-generated method stub
|
return size;
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -27,8 +32,7 @@ public class GPUDisplay implements org.warp.picalculator.gui.graphicengine.Displ
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setTitle(String title) {
|
public void setTitle(String title) {
|
||||||
// TODO Auto-generated method stub
|
wnd.window.setTitle(title);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -38,59 +42,59 @@ public class GPUDisplay implements org.warp.picalculator.gui.graphicengine.Displ
|
|||||||
}
|
}
|
||||||
wnd.window.setResizable(r);
|
wnd.window.setResizable(r);
|
||||||
wnd.window.setUndecorated(!r);
|
wnd.window.setUndecorated(!r);
|
||||||
wnd.window.setPointerVisible(r);
|
wnd.window.setPointerVisible(r);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setDisplayMode(int ww, int wh) {
|
public void setDisplayMode(int ww, int wh) {
|
||||||
|
this.size[0] = ww;
|
||||||
|
this.size[1] = wh;
|
||||||
wnd.window.setSize(ww, wh);
|
wnd.window.setSize(ww, wh);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void create() {
|
public void create() {
|
||||||
|
created = true;
|
||||||
r = new GPURenderer();
|
r = new GPURenderer();
|
||||||
wnd = new CalculatorWindow(this);
|
wnd = new NEWTWindow(this);
|
||||||
wnd.create();
|
wnd.create();
|
||||||
setDisplayMode(Main.screenSize[0], Main.screenSize[1]);
|
setDisplayMode(Main.screenSize[0], Main.screenSize[1]);
|
||||||
setResizable(Utils.debugOn&!Utils.debugThirdScreen);
|
setResizable(Utils.debugOn & !Utils.debugThirdScreen);
|
||||||
initialized = true;
|
initialized = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean wasResized() {
|
public boolean wasResized() {
|
||||||
// TODO Auto-generated method stub
|
return Main.screenSize[0] != size[0] | Main.screenSize[1] != size[1];
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getWidth() {
|
public int getWidth() {
|
||||||
// TODO Auto-generated method stub
|
return size[0];
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getHeight() {
|
public int getHeight() {
|
||||||
// TODO Auto-generated method stub
|
return size[1];
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void destroy() {
|
public void destroy() {
|
||||||
// EGL.destroy(); (Automatic)
|
initialized = false;
|
||||||
|
created = false;
|
||||||
|
wnd.window.destroy();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void start(Drawable d) {
|
public void start(Drawable d) {
|
||||||
this.d = d;
|
this.d = d;
|
||||||
wnd.window.setVisible(true);
|
wnd.window.setVisible(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void repaint() {
|
public void repaint() {
|
||||||
if (d != null) {
|
if (d != null & r != null && r.gl != null) {
|
||||||
r.gl.glClearColor(red, green, blue, alpha);
|
|
||||||
d.refresh();
|
d.refresh();
|
||||||
r.glFlush();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -99,4 +103,30 @@ public class GPUDisplay implements org.warp.picalculator.gui.graphicengine.Displ
|
|||||||
return r;
|
return r;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public RAWFont loadFont(String file) throws IOException {
|
||||||
|
return new GPUFont(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public RAWSkin loadSkin(String file) throws IOException {
|
||||||
|
return new GPUSkin(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void waitUntilExit() {
|
||||||
|
try {
|
||||||
|
do {
|
||||||
|
Thread.sleep(500);
|
||||||
|
} while(initialized | created);
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isSupported() {
|
||||||
|
return GLProfile.isAnyAvailable() == false;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
140
src/org/warp/picalculator/gui/graphicengine/gpu/GPUFont.java
Normal file
140
src/org/warp/picalculator/gui/graphicengine/gpu/GPUFont.java
Normal file
@ -0,0 +1,140 @@
|
|||||||
|
package org.warp.picalculator.gui.graphicengine.gpu;
|
||||||
|
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUFont;
|
||||||
|
|
||||||
|
import com.jogamp.opengl.GLException;
|
||||||
|
import com.jogamp.opengl.util.texture.Texture;
|
||||||
|
|
||||||
|
public class GPUFont implements RAWFont {
|
||||||
|
|
||||||
|
public Texture texture;
|
||||||
|
public int textureW;
|
||||||
|
public int textureH;
|
||||||
|
public int charW;
|
||||||
|
public int charH;
|
||||||
|
public int minCharIndex;
|
||||||
|
public int maxCharIndex;
|
||||||
|
|
||||||
|
public int memoryWidth;
|
||||||
|
public int memoryHeight;
|
||||||
|
public int memoryWidthOfEachColumn;
|
||||||
|
|
||||||
|
private boolean initialized = false;
|
||||||
|
private CPUFont tmpFont;
|
||||||
|
|
||||||
|
GPUFont(String file) throws IOException {
|
||||||
|
load(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void load(String file) throws IOException {
|
||||||
|
CPUFont font = CPUFont.loadTemporaryFont(file);
|
||||||
|
charW = font.charW;
|
||||||
|
charH = font.charH;
|
||||||
|
minCharIndex = font.minBound;
|
||||||
|
maxCharIndex = font.maxBound;
|
||||||
|
tmpFont = font;
|
||||||
|
font = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int[] getCharIndexes(String txt) {
|
||||||
|
final int l = txt.length();
|
||||||
|
final int[] indexes = new int[l];
|
||||||
|
final char[] chars = txt.toCharArray();
|
||||||
|
for (int i = 0; i < l; i++) {
|
||||||
|
indexes[i] = (chars[i] & 0xFFFF) - minCharIndex;
|
||||||
|
}
|
||||||
|
return indexes;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void genTexture(boolean[][] chars) {
|
||||||
|
final double totalChars = maxCharIndex - minCharIndex;
|
||||||
|
final int w = powerOf2((int) (Math.ceil(Math.sqrt(totalChars) * charW)));
|
||||||
|
final int h = powerOf2((int) (Math.ceil(Math.sqrt(totalChars) * charH)));
|
||||||
|
final int maxIndexW = (int) Math.floor(((double) w) / ((double) charW)) - 1;
|
||||||
|
BufferedImage bfi = new BufferedImage(w, h, BufferedImage.TYPE_INT_ARGB);
|
||||||
|
int indexX = 0;
|
||||||
|
int indexY = 0;
|
||||||
|
for (int i = 0; i < totalChars; i++) {
|
||||||
|
boolean[] currentChar = chars[i];
|
||||||
|
if (currentChar != null && currentChar.length > 0) {
|
||||||
|
for (int charY = 0; charY < charH; charY++) {
|
||||||
|
for (int charX = 0; charX < charW; charX++) {
|
||||||
|
if (currentChar[charY*charW+charX]) {
|
||||||
|
bfi.setRGB(indexX * charW + charX, indexY * charH + charY, 0xFFFFFFFF);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
indexX++;
|
||||||
|
if (indexX >= maxIndexW) {
|
||||||
|
indexX = 0;
|
||||||
|
indexY += 1;
|
||||||
|
}
|
||||||
|
currentChar = null;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
memoryWidth = w;
|
||||||
|
memoryHeight = h;
|
||||||
|
memoryWidthOfEachColumn = maxIndexW;
|
||||||
|
texture = GPURenderer.importTexture(bfi);
|
||||||
|
textureW = bfi.getWidth();
|
||||||
|
textureH = bfi.getHeight();
|
||||||
|
bfi.flush();
|
||||||
|
bfi = null;
|
||||||
|
} catch (GLException | IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private int powerOf2(int a) {
|
||||||
|
return (int) (a == 0 ? 0 : Math.pow(2, 32 - Integer.numberOfLeadingZeros(a - 1)));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void initialize(Display d) {
|
||||||
|
genTexture(tmpFont.rawchars);
|
||||||
|
tmpFont.chars32 = null;
|
||||||
|
tmpFont.rawchars = null;
|
||||||
|
tmpFont = null;
|
||||||
|
initialized = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void use(Display d) {
|
||||||
|
if (!initialized) {
|
||||||
|
initialize(d);
|
||||||
|
}
|
||||||
|
final GPURenderer r = (GPURenderer) d.getRenderer();
|
||||||
|
r.currentFont = this;
|
||||||
|
r.useTexture(texture, textureW, textureH);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getStringWidth(String text) {
|
||||||
|
final int w = (charW + 1) * text.length();
|
||||||
|
if (text.length() > 0) {
|
||||||
|
return w - 1;
|
||||||
|
} else {
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getCharacterWidth() {
|
||||||
|
return charW;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public int getCharacterHeight() {
|
||||||
|
return charH;
|
||||||
|
}
|
||||||
|
}
|
@ -2,123 +2,261 @@ package org.warp.picalculator.gui.graphicengine.gpu;
|
|||||||
|
|
||||||
import java.awt.FontMetrics;
|
import java.awt.FontMetrics;
|
||||||
import java.awt.image.BufferedImage;
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.ByteArrayInputStream;
|
||||||
|
import java.io.ByteArrayOutputStream;
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.nio.Buffer;
|
||||||
|
import java.nio.FloatBuffer;
|
||||||
|
import javax.imageio.ImageIO;
|
||||||
|
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
import org.warp.picalculator.gui.graphicengine.Renderer;
|
import org.warp.picalculator.gui.graphicengine.Renderer;
|
||||||
|
|
||||||
import com.jogamp.opengl.GL2ES2;
|
import com.jogamp.common.nio.Buffers;
|
||||||
|
import com.jogamp.opengl.GL;
|
||||||
|
import com.jogamp.opengl.GL2ES1;
|
||||||
|
import com.jogamp.opengl.GLException;
|
||||||
|
import com.jogamp.opengl.util.texture.Texture;
|
||||||
|
import com.jogamp.opengl.util.texture.TextureData;
|
||||||
|
import com.jogamp.opengl.util.texture.TextureIO;
|
||||||
|
|
||||||
public class GPURenderer implements Renderer {
|
public class GPURenderer implements Renderer {
|
||||||
|
|
||||||
public GL2ES2 gl;
|
public GL2ES1 gl;
|
||||||
|
|
||||||
|
private final DeallocationHelper deallocationHelper = new DeallocationHelper();
|
||||||
|
FloatBuffer fbVertices;
|
||||||
|
FloatBuffer txVertices;
|
||||||
|
FloatBuffer colVertices;
|
||||||
|
int fbElements;
|
||||||
|
|
||||||
|
float[] currentColor = new float[16];
|
||||||
|
float[] currentClearColorARGBf = new float[]{1f, 197f/255f, 194f/255f, 175f/255f};
|
||||||
|
boolean currentTexEnabled;
|
||||||
|
Texture currentTex;
|
||||||
|
float currentTexWidth;
|
||||||
|
float currentTexHeight;
|
||||||
|
|
||||||
|
GPUFont currentFont;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glColor3i(int r, int gg, int b) {
|
public void glColor3i(int r, int gg, int b) {
|
||||||
// TODO Auto-generated method stub
|
final float red = ((float)r) / 255f;
|
||||||
|
final float gre = ((float)gg) / 255f;
|
||||||
|
final float blu = ((float)b) / 255f;
|
||||||
|
currentColor = new float[] { red, gre, blu, 1.0f, red, gre, blu, 1.0f, red, gre, blu, 1.0f, red, gre, blu, 1.0f, };
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glColor(int c) {
|
public void glColor3f(float red, float gre, float blu) {
|
||||||
// TODO Auto-generated method stub
|
currentColor = new float[] { red, gre, blu, 1.0f, red, gre, blu, 1.0f, red, gre, blu, 1.0f, red, gre, blu, 1.0f, };
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glColor4f(float red, float gre, float blu, float alp) {
|
||||||
|
currentColor = new float[] { red, gre, blu, alp, red, gre, blu, alp, red, gre, blu, alp, red, gre, blu, alp, };
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glColor(int rgb) {
|
||||||
|
final int alpha = (rgb >> 24) & 0xFF;
|
||||||
|
final int red = (rgb >> 16) & 0xFF;
|
||||||
|
final int green = (rgb >> 8) & 0xFF;
|
||||||
|
final int blue = rgb & 0xFF;
|
||||||
|
glColor4i(red, green, blue, alpha);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int glGetClearColor() {
|
public int glGetClearColor() {
|
||||||
// TODO Auto-generated method stub
|
return (int)(currentClearColorARGBf[0] * 255) << 24 | (int)(currentClearColorARGBf[1] * 255) << 16 | (int)(currentClearColorARGBf[2] * 255) << 8 | (int)(currentClearColorARGBf[3] * 255);
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glClearColor(int c) {
|
public void glClearColor(int rgb) {
|
||||||
// TODO Auto-generated method stub
|
final float alpha = (float)((rgb >> 24) & 0xFF) / 255f;
|
||||||
|
final float red = (float)((rgb >> 16) & 0xFF) / 255f;
|
||||||
|
final float green = (float)((rgb >> 8) & 0xFF) / 255f;
|
||||||
|
final float blue = (float)(rgb & 0xFF) / 255f;
|
||||||
|
glClearColor4f(red, green, blue, alpha);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glColor4i(int red, int green, int blue, int alpha) {
|
public void glColor4i(int r, int g, int b, int a) {
|
||||||
// TODO Auto-generated method stub
|
final float red = (r) / 255f;
|
||||||
|
final float gre = (g) / 255f;
|
||||||
|
final float blu = (b) / 255f;
|
||||||
|
final float alp = (a) / 255f;
|
||||||
|
currentColor = new float[] { red, gre, blu, alp, red, gre, blu, alp, red, gre, blu, alp, red, gre, blu, alp, };
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glClearColor(int red, int green, int blue, int alpha) {
|
public void glClearColor4i(int red, int green, int blue, int alpha) {
|
||||||
// TODO Auto-generated method stub
|
final float ros = (red) / 255f;
|
||||||
|
final float gre = (green) / 255f;
|
||||||
|
final float blu = (blue) / 255f;
|
||||||
|
final float alp = (alpha) / 255f;
|
||||||
|
currentClearColorARGBf = new float[]{alp, ros, gre, blu};
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glClear() {
|
public void glClearColor4f(float red, float green, float blue, float alpha) {
|
||||||
// TODO Auto-generated method stub
|
currentClearColorARGBf = new float[]{alpha, red, green, blue};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glDrawSkin(int skinwidth, int[] skin, int x0, int y0, int s0, int t0, int s1, int t1,
|
public void glClear(int screenWidth, int screenHeight) {
|
||||||
boolean transparent) {
|
glColor(glGetClearColor());
|
||||||
// TODO Auto-generated method stub
|
glFillColor(0, 0, screenWidth, screenHeight);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glDrawLine(int x0, int y0, int x1, int y1) {
|
public void glDrawLine(int x0, int y0, int x1, int y1) {
|
||||||
// TODO Auto-generated method stub
|
glFillColor(x0, y0, x1-x0+1, y1-y0+1);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glFillRect(int x0, int y0, int w1, int h1) {
|
public void glFillRect(int x, int y, int width, int height, float uvX, float uvY, float uvWidth, float uvHeight) {
|
||||||
// TODO Auto-generated method stub
|
enableTexture();
|
||||||
|
uvWidth/=currentTexWidth;
|
||||||
|
uvX/=currentTexWidth;
|
||||||
|
uvHeight/=currentTexHeight;
|
||||||
|
uvY = 1 - uvY/currentTexHeight - uvHeight;
|
||||||
|
final float[] vertices = { x, y, 0.0f, x, y + height, 0.0f, x + width, y, 0.0f, x + width, y + height, 0.0f, };
|
||||||
|
final float[] tex_vertices = { uvX, uvY + uvHeight, uvX, uvY, uvX + uvWidth, uvY + uvHeight, uvX + uvWidth, uvY, };
|
||||||
|
fbElements++;
|
||||||
|
fbVertices.put(vertices);
|
||||||
|
txVertices.put(tex_vertices);
|
||||||
|
colVertices.put(currentColor);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int[] getMatrixOfImage(BufferedImage bufferedImage) {
|
public void glFillColor(int x0, int y0, int w1, int h1) {
|
||||||
// TODO Auto-generated method stub
|
disableTexture();
|
||||||
return null;
|
final float[] vertices = { x0, y0, 0.0f, x0, y0 + h1, 0.0f, x0 + w1, y0, 0.0f, x0 + w1, y0 + h1, 0.0f, };
|
||||||
|
final float[] tex_vertices = { 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1.0f, 0.0f, };
|
||||||
|
fbElements++;
|
||||||
|
fbVertices.put(vertices);
|
||||||
|
txVertices.put(tex_vertices);
|
||||||
|
colVertices.put(currentColor);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glDrawStringLeft(int x, int y, String text) {
|
public void glDrawStringLeft(int x, int y, String text) {
|
||||||
// TODO Auto-generated method stub
|
final int txtLen = text.length();
|
||||||
|
int[] txtArray = currentFont.getCharIndexes(text);
|
||||||
|
int tableIndexX;
|
||||||
|
int tableIndexY;
|
||||||
|
for (int currentCharIndex = 0; currentCharIndex < txtLen; currentCharIndex++) {
|
||||||
|
tableIndexX = txtArray[currentCharIndex] % currentFont.memoryWidthOfEachColumn;
|
||||||
|
tableIndexY = (txtArray[currentCharIndex] - tableIndexX) / currentFont.memoryWidthOfEachColumn;
|
||||||
|
glFillRect(x + currentCharIndex * (currentFont.charW + 1), y, currentFont.charW, currentFont.charH, tableIndexX*currentFont.charW, tableIndexY*currentFont.charH, currentFont.charW, currentFont.charH);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glDrawStringCenter(int x, int y, String text) {
|
public void glDrawStringCenter(int x, int y, String text) {
|
||||||
// TODO Auto-generated method stub
|
glDrawStringLeft(x - (currentFont.getStringWidth(text) / 2), y, text);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void glDrawStringRight(int x, int y, String text) {
|
public void glDrawStringRight(int x, int y, String text) {
|
||||||
// TODO Auto-generated method stub
|
glDrawStringLeft(x - currentFont.getStringWidth(text), y, text);
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void glSetFont(RAWFont font) {
|
|
||||||
// TODO Auto-generated method stub
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int glGetStringWidth(RAWFont rf, String text) {
|
|
||||||
// TODO Auto-generated method stub
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int glGetFontWidth(FontMetrics fm, String text) {
|
|
||||||
// TODO Auto-generated method stub
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public RAWFont getCurrentFont() {
|
public RAWFont getCurrentFont() {
|
||||||
// TODO Auto-generated method stub
|
return currentFont;
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static Texture importTexture(GL gl, String string) throws IOException {
|
||||||
|
final FileInputStream f = new FileInputStream("test.png");
|
||||||
|
final TextureData tx_dat = TextureIO.newTextureData(gl.getGLProfile(), f, false, TextureIO.PNG);
|
||||||
|
final Texture tex = new Texture(gl, tx_dat);
|
||||||
|
tex.setTexParameteri(gl, GL.GL_TEXTURE_MIN_FILTER, GL.GL_LINEAR);
|
||||||
|
tex.setTexParameteri(gl, GL.GL_TEXTURE_MAG_FILTER, GL.GL_NEAREST);
|
||||||
|
tex.setTexParameteri(gl, GL.GL_TEXTURE_WRAP_S, GL.GL_CLAMP_TO_EDGE);
|
||||||
|
tex.setTexParameteri(gl, GL.GL_TEXTURE_WRAP_T, GL.GL_CLAMP_TO_EDGE);
|
||||||
|
return tex;
|
||||||
|
}
|
||||||
|
|
||||||
|
static BufferedImage openTexture(String file) throws GLException, IOException {
|
||||||
|
final ByteArrayOutputStream os = new ByteArrayOutputStream();
|
||||||
|
return ImageIO.read(GPURenderer.class.getClassLoader().getResource(file));
|
||||||
|
}
|
||||||
|
|
||||||
|
static Texture importTexture(BufferedImage img) throws GLException, IOException {
|
||||||
|
final ByteArrayOutputStream os = new ByteArrayOutputStream();
|
||||||
|
ImageIO.write(img, "png", os);
|
||||||
|
final InputStream fis = new ByteArrayInputStream(os.toByteArray());
|
||||||
|
return TextureIO.newTexture(fis, false, TextureIO.PNG);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void glClearSkin() {
|
||||||
|
if (currentTex != null) {
|
||||||
|
currentTex = null;
|
||||||
|
endDrawCycle();
|
||||||
|
startDrawCycle();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void startDrawCycle() {
|
||||||
|
fbVertices = Buffers.newDirectFloatBuffer(3 * 4);
|
||||||
|
txVertices = Buffers.newDirectFloatBuffer(2 * 4);
|
||||||
|
colVertices = Buffers.newDirectFloatBuffer(4 * 4);
|
||||||
|
fbElements = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void endDrawCycle() {
|
||||||
|
fbVertices.rewind();
|
||||||
|
txVertices.rewind();
|
||||||
|
colVertices.rewind();
|
||||||
|
|
||||||
|
gl.glColorPointer(4, GL.GL_FLOAT, 0, colVertices);
|
||||||
|
gl.glTexCoordPointer(2, GL.GL_FLOAT, 0, txVertices);
|
||||||
|
gl.glVertexPointer(3, GL.GL_FLOAT, 0, fbVertices);
|
||||||
|
|
||||||
|
if (currentTexEnabled) {
|
||||||
|
gl.glEnable(GL2ES1.GL_TEXTURE_2D);
|
||||||
|
currentTex.bind(gl);
|
||||||
|
} else {
|
||||||
|
gl.glDisable(GL2ES1.GL_TEXTURE_2D);
|
||||||
|
}
|
||||||
|
|
||||||
|
gl.glDrawArrays(GL.GL_TRIANGLE_STRIP, 0, 4);
|
||||||
|
|
||||||
|
deleteBuffer(fbVertices);
|
||||||
|
deleteBuffer(txVertices);
|
||||||
|
deleteBuffer(colVertices);
|
||||||
|
fbVertices = null;
|
||||||
|
txVertices = null;
|
||||||
|
colVertices = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void deleteBuffer(final Buffer realNioBuffer) {
|
||||||
|
if (deallocationHelper != null) {
|
||||||
|
deallocationHelper.deallocate(realNioBuffer);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void disableTexture() {
|
||||||
|
endDrawCycle();
|
||||||
|
startDrawCycle();
|
||||||
|
currentTexEnabled = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void enableTexture() {
|
||||||
|
endDrawCycle();
|
||||||
|
startDrawCycle();
|
||||||
|
currentTexEnabled = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void useTexture(Texture t, float w, float h) {
|
||||||
|
enableTexture();
|
||||||
|
currentTex = t;
|
||||||
|
currentTexWidth = w;
|
||||||
|
currentTexHeight = h;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
58
src/org/warp/picalculator/gui/graphicengine/gpu/GPUSkin.java
Normal file
58
src/org/warp/picalculator/gui/graphicengine/gpu/GPUSkin.java
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
package org.warp.picalculator.gui.graphicengine.gpu;
|
||||||
|
|
||||||
|
import java.awt.image.BufferedImage;
|
||||||
|
import java.io.IOException;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
|
|
||||||
|
import com.jogamp.opengl.GL2ES1;
|
||||||
|
import com.jogamp.opengl.GLException;
|
||||||
|
import com.jogamp.opengl.util.texture.Texture;
|
||||||
|
|
||||||
|
public class GPUSkin implements RAWSkin {
|
||||||
|
|
||||||
|
public Texture t;
|
||||||
|
public int w;
|
||||||
|
public int h;
|
||||||
|
|
||||||
|
private String texturePath;
|
||||||
|
private boolean initialized = false;
|
||||||
|
|
||||||
|
GPUSkin(String file) throws IOException {
|
||||||
|
load(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void load(String file) throws IOException {
|
||||||
|
if ((this.getClass().getClassLoader().getResource(file)) == null) {
|
||||||
|
throw new IOException("File '" + file + "' not found!");
|
||||||
|
}
|
||||||
|
texturePath = file;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void initialize(Display d) {
|
||||||
|
try {
|
||||||
|
BufferedImage i = GPURenderer.openTexture(texturePath);
|
||||||
|
GL2ES1 gl = ((GPURenderer)d.getRenderer()).gl;
|
||||||
|
t = GPURenderer.importTexture(i);
|
||||||
|
w = i.getWidth();
|
||||||
|
h = i.getHeight();
|
||||||
|
t.setTexParameteri(gl, GL2ES1.GL_TEXTURE_MAG_FILTER, GL2ES1.GL_NEAREST);
|
||||||
|
initialized = true;
|
||||||
|
} catch (GLException | IOException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
System.exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void use(Display d) {
|
||||||
|
if (!initialized) {
|
||||||
|
initialize(d);
|
||||||
|
}
|
||||||
|
final GPURenderer r = (GPURenderer) d.getRenderer();
|
||||||
|
r.useTexture(t,w,h);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
381
src/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
Normal file
381
src/org/warp/picalculator/gui/graphicengine/gpu/NEWTWindow.java
Normal file
@ -0,0 +1,381 @@
|
|||||||
|
/**
|
||||||
|
* Copyright 2012-2013 JogAmp Community. All rights reserved.
|
||||||
|
*
|
||||||
|
* Redistribution and use in source and binary forms, with or without modification, are
|
||||||
|
* permitted provided that the following conditions are met:
|
||||||
|
*
|
||||||
|
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||||
|
* conditions and the following disclaimer.
|
||||||
|
*
|
||||||
|
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||||
|
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||||
|
* provided with the distribution.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||||
|
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||||
|
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
|
||||||
|
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||||
|
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||||
|
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||||
|
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||||
|
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*
|
||||||
|
* The views and conclusions contained in the software and documentation are those of the
|
||||||
|
* authors and should not be interpreted as representing official policies, either expressed
|
||||||
|
* or implied, of JogAmp Community.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.warp.picalculator.gui.graphicengine.gpu;
|
||||||
|
|
||||||
|
import com.jogamp.opengl.GL;
|
||||||
|
import com.jogamp.opengl.GL2ES1;
|
||||||
|
import com.jogamp.opengl.GLAutoDrawable;
|
||||||
|
import com.jogamp.opengl.GLEventListener;
|
||||||
|
import com.jogamp.opengl.GLProfile;
|
||||||
|
import com.jogamp.opengl.fixedfunc.GLMatrixFunc;
|
||||||
|
import com.jogamp.opengl.fixedfunc.GLPointerFunc;
|
||||||
|
import com.jogamp.opengl.GLCapabilities;
|
||||||
|
import com.jogamp.newt.event.KeyEvent;
|
||||||
|
import com.jogamp.newt.event.KeyListener;
|
||||||
|
import com.jogamp.newt.event.WindowEvent;
|
||||||
|
import com.jogamp.newt.event.WindowListener;
|
||||||
|
import com.jogamp.newt.event.WindowUpdateEvent;
|
||||||
|
import com.jogamp.newt.opengl.GLWindow;
|
||||||
|
|
||||||
|
import com.jogamp.opengl.util.*;
|
||||||
|
|
||||||
|
import java.awt.event.ComponentEvent;
|
||||||
|
import java.awt.event.ComponentListener;
|
||||||
|
|
||||||
|
import org.warp.picalculator.device.Keyboard;
|
||||||
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Display;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* <pre>
|
||||||
|
* __ __|_ ___________________________________________________________________________ ___|__ __
|
||||||
|
* // /\ _ /\ \\
|
||||||
|
* //____/ \__ __ _____ _____ _____ _____ _____ | | __ _____ _____ __ __/ \____\\
|
||||||
|
* \ \ / / __| | | __| _ | | _ | | | __| | | __| | /\ \ / /
|
||||||
|
* \____\/_/ | | | | | | | | | | | __| | | | | | | | | | |__ " \_\/____/
|
||||||
|
* /\ \ |_____|_____|_____|__|__|_|_|_|__| | | |_____|_____|_____|_____| _ / /\
|
||||||
|
* / \____\ http://jogamp.org |_| /____/ \
|
||||||
|
* \ / "' _________________________________________________________________________ `" \ /
|
||||||
|
* \/____. .____\/
|
||||||
|
* </pre>
|
||||||
|
*
|
||||||
|
* <p>
|
||||||
|
* JOGL2 OpenGL ES 2 demo to expose and learn what the RAW OpenGL ES 2 API looks
|
||||||
|
* like.
|
||||||
|
*
|
||||||
|
* Compile, run and enjoy:
|
||||||
|
* wget
|
||||||
|
* http://jogamp.org/deployment/jogamp-current/archive/jogamp-all-platforms.7z
|
||||||
|
* 7z x jogamp-all-platforms.7z
|
||||||
|
* cd jogamp-all-platforms
|
||||||
|
* mkdir -p demos/es2
|
||||||
|
* cd demos/es2
|
||||||
|
* wget
|
||||||
|
* https://raw.github.com/xranby/jogl-demos/master/src/demos/es2/RawGL2ES1demo.java
|
||||||
|
* cd ../..
|
||||||
|
* javac -cp jar/jogl-all.jar:jar/gluegen-rt.jar demos/es2/RawGL2ES1demo.java
|
||||||
|
* java -cp jar/jogl-all.jar:jar/gluegen-rt.jar:. demos.es2.RawGL2ES1demo
|
||||||
|
* </p>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* @author Xerxes Rånby (xranby)
|
||||||
|
*/
|
||||||
|
|
||||||
|
public class NEWTWindow implements GLEventListener {
|
||||||
|
|
||||||
|
private final GPUDisplay disp;
|
||||||
|
private final GPURenderer renderer;
|
||||||
|
|
||||||
|
public NEWTWindow(GPUDisplay disp) {
|
||||||
|
this.disp = disp;
|
||||||
|
renderer = disp.getRenderer();
|
||||||
|
}
|
||||||
|
|
||||||
|
public GLWindow window;
|
||||||
|
|
||||||
|
public void create() {
|
||||||
|
/* This demo are based on the GL2ES1 GLProfile that uses common hardware acceleration
|
||||||
|
* functionality of desktop OpenGL 3, 2 and mobile OpenGL ES 2 devices.
|
||||||
|
* JogAmp JOGL will probe all the installed libGL.so, libEGL.so and libGLESv2.so librarys on
|
||||||
|
* the system to find which one provide hardware acceleration for your GPU device.
|
||||||
|
* Its common to find more than one version of these librarys installed on a system.
|
||||||
|
* For example on a ARM Linux system JOGL may find
|
||||||
|
* Hardware accelerated Nvidia tegra GPU drivers in: /usr/lib/nvidia-tegra/libEGL.so
|
||||||
|
* Software rendered Mesa Gallium driver in: /usr/lib/arm-linux-gnueabi/mesa-egl/libEGL.so.1
|
||||||
|
* Software rendered Mesa X11 in: /usr/lib/arm-linux-gnueabi/mesa/libGL.so
|
||||||
|
* Good news!: JOGL does all this probing for you all you have to do are to ask for
|
||||||
|
* the GLProfile you want to use.
|
||||||
|
*/
|
||||||
|
|
||||||
|
System.out.println("Loading OpenGL...");
|
||||||
|
System.out.println(GLProfile.glAvailabilityToString());
|
||||||
|
if (GLProfile.isAnyAvailable()) {
|
||||||
|
System.err.println("Le OpenGL non sono presenti su questo computer!");
|
||||||
|
}
|
||||||
|
final GLCapabilities caps = new GLCapabilities(GLProfile.get(GLProfile.GL2ES1));
|
||||||
|
System.out.println("Loaded OpenGL");
|
||||||
|
// We may at this point tweak the caps and request a translucent drawable
|
||||||
|
caps.setBackgroundOpaque(true); //transparency window
|
||||||
|
final GLWindow glWindow = GLWindow.create(caps);
|
||||||
|
window = glWindow;
|
||||||
|
|
||||||
|
glWindow.setTitle("Algebraic Calculator for Raspberry PI by Andrea Cavalli (XDrake99)");
|
||||||
|
|
||||||
|
glWindow.addWindowListener(new WindowListener() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowDestroyNotify(WindowEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowDestroyed(WindowEvent e) {
|
||||||
|
DisplayManager.display.destroy();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowGainedFocus(WindowEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowLostFocus(WindowEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowMoved(WindowEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowRepaint(WindowUpdateEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void windowResized(WindowEvent e) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
glWindow.addKeyListener(new KeyListener() {
|
||||||
|
@Override
|
||||||
|
public void keyPressed(KeyEvent arg0) {
|
||||||
|
Keyboard.debugKeyCode = arg0.getKeyCode();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void keyReleased(KeyEvent arg0) {
|
||||||
|
switch (arg0.getKeyCode()) {
|
||||||
|
case KeyEvent.VK_ESCAPE:
|
||||||
|
Keyboard.keyReleased(Key.POWER);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_D:
|
||||||
|
Keyboard.keyReleased(Key.debug_DEG);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_R:
|
||||||
|
Keyboard.keyReleased(Key.debug_RAD);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_G:
|
||||||
|
Keyboard.keyReleased(Key.debug_GRA);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_X:
|
||||||
|
if (Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.LETTER_X);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_P:
|
||||||
|
if (Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.PI);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_B:
|
||||||
|
if (Keyboard.shift) {
|
||||||
|
Keyboard.keyReleased(Key.BRIGHTNESS_CYCLE_REVERSE);
|
||||||
|
} else if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.BRIGHTNESS_CYCLE);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_ENTER:
|
||||||
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.SOLVE);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
int row = 2;
|
||||||
|
int col = 1;
|
||||||
|
Keyboard.debugKeysDown[row - 1][col - 1] = false;
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_1:
|
||||||
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.debug1);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_2:
|
||||||
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.debug2);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_3:
|
||||||
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.debug3);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_4:
|
||||||
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.debug4);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_5:
|
||||||
|
if (!Keyboard.shift && !Keyboard.alpha) {
|
||||||
|
Keyboard.keyReleased(Key.debug5);
|
||||||
|
} else {
|
||||||
|
Keyboard.keyReleased(Key.NONE);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case 0x15:
|
||||||
|
case KeyEvent.VK_SHIFT:
|
||||||
|
Keyboard.keyReleased(Key.SHIFT);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_A:
|
||||||
|
Keyboard.keyReleased(Key.ALPHA);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_M:
|
||||||
|
Keyboard.keyPressed(Key.SURD_MODE);
|
||||||
|
break;
|
||||||
|
case KeyEvent.VK_LEFT:
|
||||||
|
//LEFT
|
||||||
|
row = 2;
|
||||||
|
col = 3;
|
||||||
|
Keyboard.debugKeysDown[row - 1][col - 1] = false;
|
||||||
|
case KeyEvent.VK_RIGHT:
|
||||||
|
//RIGHT
|
||||||
|
row = 2;
|
||||||
|
col = 5;
|
||||||
|
Keyboard.debugKeysDown[row - 1][col - 1] = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
glWindow.addGLEventListener(this /* GLEventListener */);
|
||||||
|
final Animator animator = new Animator();
|
||||||
|
animator.add(glWindow);
|
||||||
|
animator.start();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void init(GLAutoDrawable drawable) {
|
||||||
|
final GL2ES1 gl = drawable.getGL().getGL2ES1();
|
||||||
|
|
||||||
|
//Vsync
|
||||||
|
gl.setSwapInterval(2);
|
||||||
|
|
||||||
|
//Textures
|
||||||
|
gl.glEnable(GL.GL_TEXTURE_2D);
|
||||||
|
|
||||||
|
//Transparency
|
||||||
|
gl.glEnable(GL2ES1.GL_BLEND);
|
||||||
|
gl.glBlendFunc(GL2ES1.GL_SRC_ALPHA, GL2ES1.GL_ONE_MINUS_SRC_ALPHA);
|
||||||
|
|
||||||
|
try {
|
||||||
|
renderer.currentTex = ((GPUSkin) disp.loadSkin("test.png")).t;
|
||||||
|
} catch (final Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
System.err.println("Chosen GLCapabilities: " + drawable.getChosenGLCapabilities());
|
||||||
|
System.err.println("INIT GL IS: " + gl.getClass().getName());
|
||||||
|
System.err.println("GL_VENDOR: " + gl.glGetString(GL.GL_VENDOR));
|
||||||
|
System.err.println("GL_RENDERER: " + gl.glGetString(GL.GL_RENDERER));
|
||||||
|
System.err.println("GL_VERSION: " + gl.glGetString(GL.GL_VERSION));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void reshape(GLAutoDrawable glad, int x, int y, int width, int height) {
|
||||||
|
disp.size[0] = width;
|
||||||
|
disp.size[1] = height;
|
||||||
|
final GL2ES1 gl = glad.getGL().getGL2ES1();
|
||||||
|
float max_wh, min_wh;
|
||||||
|
if (width == 0) {
|
||||||
|
width = 1;
|
||||||
|
}
|
||||||
|
if (height == 0) {
|
||||||
|
height = 1;
|
||||||
|
}
|
||||||
|
if (width > height) {
|
||||||
|
max_wh = width;
|
||||||
|
min_wh = height;
|
||||||
|
} else {
|
||||||
|
max_wh = height;
|
||||||
|
min_wh = width;
|
||||||
|
}
|
||||||
|
|
||||||
|
gl.glViewport(0, 0, width, height);
|
||||||
|
|
||||||
|
gl.glMatrixMode(GLMatrixFunc.GL_PROJECTION);
|
||||||
|
gl.glLoadIdentity();
|
||||||
|
|
||||||
|
gl.glOrtho(0.0, width, height, 0.0, -1, 1);
|
||||||
|
|
||||||
|
gl.glMatrixMode(GLMatrixFunc.GL_MODELVIEW);
|
||||||
|
gl.glLoadIdentity();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void display(GLAutoDrawable glad) {
|
||||||
|
final GL2ES1 gl = glad.getGL().getGL2ES1();
|
||||||
|
|
||||||
|
renderer.gl = gl;
|
||||||
|
|
||||||
|
gl.glEnableClientState(GLPointerFunc.GL_COLOR_ARRAY);
|
||||||
|
gl.glEnableClientState(GLPointerFunc.GL_VERTEX_ARRAY);
|
||||||
|
gl.glEnableClientState(GLPointerFunc.GL_TEXTURE_COORD_ARRAY);
|
||||||
|
|
||||||
|
renderer.startDrawCycle();
|
||||||
|
|
||||||
|
disp.repaint();
|
||||||
|
|
||||||
|
renderer.endDrawCycle();
|
||||||
|
|
||||||
|
renderer.gl = null;
|
||||||
|
|
||||||
|
gl.glDisableClientState(GLPointerFunc.GL_COLOR_ARRAY);
|
||||||
|
gl.glDisableClientState(GLPointerFunc.GL_TEXTURE_COORD_ARRAY);
|
||||||
|
gl.glDisableClientState(GLPointerFunc.GL_VERTEX_ARRAY);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void dispose(GLAutoDrawable drawable) {
|
||||||
|
System.out.println("cleanup");
|
||||||
|
final GL2ES1 gl = drawable.getGL().getGL2ES1();
|
||||||
|
System.exit(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -1,15 +1,16 @@
|
|||||||
package org.warp.picalculator.gui.screens;
|
package org.warp.picalculator.gui.screens;
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.functions.Function;
|
import org.warp.picalculator.math.functions.Function;
|
||||||
import org.warp.picalculator.math.functions.Variable.VariableValue;
|
import org.warp.picalculator.math.functions.Variable.VariableValue;
|
||||||
|
|
||||||
public class ChooseVariableValueScreen extends Screen {
|
public class ChooseVariableValueScreen extends Screen {
|
||||||
|
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
private MathInputScreen es;
|
private final MathInputScreen es;
|
||||||
public Function resultNumberValue;
|
public Function resultNumberValue;
|
||||||
|
|
||||||
public ChooseVariableValueScreen(MathInputScreen es, VariableValue variableValue) {
|
public ChooseVariableValueScreen(MathInputScreen es, VariableValue variableValue) {
|
||||||
@ -20,20 +21,28 @@ public class ChooseVariableValueScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void created() throws InterruptedException {
|
public void created() throws InterruptedException {}
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() throws InterruptedException {}
|
public void init() throws InterruptedException {}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void render() {
|
public void render() {
|
||||||
PIDisplay.renderer.glColor4i(0, 0, 0, 64);
|
Utils.getFont(false, true).use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2+1, Main.screenSize[1]/4, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glColor4i(0, 0, 0, 64);
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2, Main.screenSize[1]/4+1, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2 + 1, Main.screenSize[1] / 2 - 20, "WORK IN PROGRESS.");
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2+1, Main.screenSize[1]/4+1, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2, Main.screenSize[1] / 2 - 20 + 1, "WORK IN PROGRESS.");
|
||||||
PIDisplay.renderer.glColor3i(255, 0, 0);
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2 + 1, Main.screenSize[1] / 2 - 20 + 1, "WORK IN PROGRESS.");
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2, Main.screenSize[1]/4, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glColor3i(255, 0, 0);
|
||||||
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2, Main.screenSize[1] / 2 - 20, "WORK IN PROGRESS.");
|
||||||
|
|
||||||
|
Utils.getFont(false, false).use(DisplayManager.display);
|
||||||
|
DisplayManager.renderer.glColor4i(0, 0, 0, 64);
|
||||||
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2 + 1, Main.screenSize[1] / 2, "THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2, Main.screenSize[1] / 2 + 1, "THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2 + 1, Main.screenSize[1] / 2 + 1, "THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
|
DisplayManager.renderer.glColor3i(255, 0, 0);
|
||||||
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2, Main.screenSize[1] / 2, "THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -1,12 +1,11 @@
|
|||||||
package org.warp.picalculator.gui.screens;
|
package org.warp.picalculator.gui.screens;
|
||||||
|
|
||||||
import static org.warp.picalculator.device.graphicengine.cpu.CPUDisplay.Render.*;
|
import static org.warp.picalculator.gui.DisplayManager.fonts;
|
||||||
import static org.warp.picalculator.gui.PIDisplay.colore;
|
|
||||||
import static org.warp.picalculator.gui.PIDisplay.fonts;
|
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Renderer;
|
||||||
|
|
||||||
public class KeyboardDebugScreen extends Screen {
|
public class KeyboardDebugScreen extends Screen {
|
||||||
|
|
||||||
@ -14,7 +13,7 @@ public class KeyboardDebugScreen extends Screen {
|
|||||||
public String keyevent;
|
public String keyevent;
|
||||||
public static int keyX;
|
public static int keyX;
|
||||||
public static int keyY;
|
public static int keyY;
|
||||||
public static String[] log = new String[]{"POWER ON","LOADING","LOADED","DONE","---"};
|
public static String[] log = new String[] { "POWER ON", "LOADING", "LOADED", "DONE", "---" };
|
||||||
public long beforetime;
|
public long beforetime;
|
||||||
|
|
||||||
public KeyboardDebugScreen() {
|
public KeyboardDebugScreen() {
|
||||||
@ -23,141 +22,140 @@ public class KeyboardDebugScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void created() throws InterruptedException {
|
public void created() throws InterruptedException {}
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() throws InterruptedException {
|
public void init() throws InterruptedException {}
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void render() {
|
public void render() {
|
||||||
PIDisplay.renderer.glSetFont(fonts[2]);
|
Renderer renderer = DisplayManager.renderer;
|
||||||
colore(0.75f, 0.0f, 0.0f, 1.0f);
|
fonts[2].use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawStringRight(Main.screenSize[0] - 10, 30, "-" + keyevent.toUpperCase() + "-");
|
renderer.glColor4f(0.75f, 0.0f, 0.0f, 1.0f);
|
||||||
|
renderer.glDrawStringRight(Main.screenSize[0] - 10, 30, "-" + keyevent.toUpperCase() + "-");
|
||||||
if (keyevent != "NONE") {
|
if (keyevent != "NONE") {
|
||||||
PIDisplay.renderer.glSetFont(fonts[2]);
|
fonts[2].use(DisplayManager.display);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringLeft(10, 30, "Key position");
|
renderer.glDrawStringLeft(10, 30, "Key position");
|
||||||
PIDisplay.renderer.glDrawStringLeft(10, 45, "X: " + keyX + ", Y:" + keyY);
|
renderer.glDrawStringLeft(10, 45, "X: " + keyX + ", Y:" + keyY);
|
||||||
PIDisplay.renderer.glDrawStringLeft(10, 65, "Key value");
|
renderer.glDrawStringLeft(10, 65, "Key value");
|
||||||
PIDisplay.renderer.glDrawStringLeft(10, 80, key);
|
renderer.glDrawStringLeft(10, 80, key);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glSetFont(fonts[3]);
|
fonts[3].use(DisplayManager.display);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
for (int i = 0; i < 5; i++) {
|
for (int i = 0; i < 5; i++) {
|
||||||
if (log[i] != null) {
|
if (log[i] != null) {
|
||||||
PIDisplay.renderer.glDrawStringLeft(10, 230 + 15*(i+1), log[i].toUpperCase());
|
renderer.glDrawStringLeft(10, 230 + 15 * (i + 1), log[i].toUpperCase());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//FROM SERIAL
|
//FROM SERIAL
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glFillRect(-80+100+200, 90, 5, 5);
|
renderer.glFillColor(-80 + 100 + 200, 90, 5, 5);
|
||||||
PIDisplay.renderer.glFillRect(-80+100, 100, 200, 70);
|
renderer.glFillColor(-80 + 100, 100, 200, 70);
|
||||||
PIDisplay.renderer.glSetFont(fonts[2]);
|
fonts[2].use(DisplayManager.display);
|
||||||
colore(1.0f, 1.0f, 1.0f, 1.0f);
|
renderer.glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(-80+100+200/2, 100+70/2-(PIDisplay.renderer.getCurrentFont().charH/2), "FROM SERIAL");
|
renderer.glDrawStringCenter(-80 + 100 + 200 / 2, 100 + 70 / 2 - (renderer.getCurrentFont().getCharacterHeight() / 2), "FROM SERIAL");
|
||||||
PIDisplay.renderer.glSetFont(fonts[3]);
|
fonts[3].use(DisplayManager.display);
|
||||||
colore(0.0f, 0.0f, 1.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 1.0f, 1.0f);
|
||||||
for (int i = 0; i < 8; i++) {
|
for (int i = 0; i < 8; i++) {
|
||||||
if (pinsA[i] == 1) {
|
if (pinsA[i] == 1) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else if (pinsA[i] == 2) {
|
} else if (pinsA[i] == 2) {
|
||||||
colore(0.5f, 0.5f, 1.0f, 1.0f);
|
renderer.glColor4f(0.5f, 0.5f, 1.0f, 1.0f);
|
||||||
} else if (pinsA[i] == -1) {
|
} else if (pinsA[i] == -1) {
|
||||||
colore(0.7f, 0.7f, 0.7f, 1.0f);
|
renderer.glColor4f(0.7f, 0.7f, 0.7f, 1.0f);
|
||||||
} else if (pinsA[i] == 0) {
|
} else if (pinsA[i] == 0) {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(-80+103+25*(7-i), 80, 20, 20);
|
renderer.glFillColor(-80 + 103 + 25 * (7 - i), 80, 20, 20);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(-80+113+25*(7-i), 90-(PIDisplay.renderer.getCurrentFont().charH/2), ""+(i+1));
|
renderer.glDrawStringCenter(-80 + 113 + 25 * (7 - i), 90 - (renderer.getCurrentFont().getCharacterHeight() / 2), "" + (i + 1));
|
||||||
}
|
}
|
||||||
for (int i = 15; i >= 8; i--) {
|
for (int i = 15; i >= 8; i--) {
|
||||||
if (pinsA[i] == 1) {
|
if (pinsA[i] == 1) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else if (pinsA[i] == 2) {
|
} else if (pinsA[i] == 2) {
|
||||||
colore(0.5f, 0.5f, 1.0f, 1.0f);
|
renderer.glColor4f(0.5f, 0.5f, 1.0f, 1.0f);
|
||||||
} else if (pinsA[i] == -1) {
|
} else if (pinsA[i] == -1) {
|
||||||
colore(0.7f, 0.7f, 0.7f, 1.0f);
|
renderer.glColor4f(0.7f, 0.7f, 0.7f, 1.0f);
|
||||||
} else if (pinsA[i] == 0) {
|
} else if (pinsA[i] == 0) {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(-80+103+25*(i-8), 170, 20, 20);
|
renderer.glFillColor(-80 + 103 + 25 * (i - 8), 170, 20, 20);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(-80+113+25*(i-8), 180-(PIDisplay.renderer.getCurrentFont().charH/2), ""+(i+1));
|
renderer.glDrawStringCenter(-80 + 113 + 25 * (i - 8), 180 - (renderer.getCurrentFont().getCharacterHeight() / 2), "" + (i + 1));
|
||||||
}
|
}
|
||||||
for (int i = 0; i < 8; i++) {
|
for (int i = 0; i < 8; i++) {
|
||||||
if (dataA[i]) {
|
if (dataA[i]) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else {
|
} else {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(-80+160+10*(i), 150, 8, 8);
|
renderer.glFillColor(-80 + 160 + 10 * (i), 150, 8, 8);
|
||||||
}
|
}
|
||||||
|
|
||||||
//TO SERIAL
|
//TO SERIAL
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glFillRect(150+90, 200, 5, 5);
|
renderer.glFillColor(150 + 90, 200, 5, 5);
|
||||||
PIDisplay.renderer.glFillRect(150+100, 100, 200, 70);
|
renderer.glFillColor(150 + 100, 100, 200, 70);
|
||||||
PIDisplay.renderer.glSetFont(fonts[2]);
|
fonts[2].use(DisplayManager.display);
|
||||||
colore(1.0f, 1.0f, 1.0f, 1.0f);
|
renderer.glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(150+100+200/2, 100+70/2-(PIDisplay.renderer.getCurrentFont().charH/2), "TO SERIAL");
|
renderer.glDrawStringCenter(150 + 100 + 200 / 2, 100 + 70 / 2 - (renderer.getCurrentFont().getCharacterHeight() / 2), "TO SERIAL");
|
||||||
PIDisplay.renderer.glSetFont(fonts[3]);
|
fonts[3].use(DisplayManager.display);
|
||||||
colore(0.0f, 0.0f, 1.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 1.0f, 1.0f);
|
||||||
for (int i = 15; i >= 8; i--) {
|
for (int i = 15; i >= 8; i--) {
|
||||||
if (pinsB[i] == 1) {
|
if (pinsB[i] == 1) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else if (pinsB[i] == 2) {
|
} else if (pinsB[i] == 2) {
|
||||||
colore(0.5f, 0.5f, 1.0f, 1.0f);
|
renderer.glColor4f(0.5f, 0.5f, 1.0f, 1.0f);
|
||||||
} else if (pinsB[i] == -1) {
|
} else if (pinsB[i] == -1) {
|
||||||
colore(0.7f, 0.7f, 0.7f, 1.0f);
|
renderer.glColor4f(0.7f, 0.7f, 0.7f, 1.0f);
|
||||||
} else if (pinsB[i] == 0) {
|
} else if (pinsB[i] == 0) {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(150+103+25*(15-i), 80, 20, 20);
|
renderer.glFillColor(150 + 103 + 25 * (15 - i), 80, 20, 20);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(150+113+25*(15-i), 90-(PIDisplay.renderer.getCurrentFont().charH/2), ""+(i+1));
|
renderer.glDrawStringCenter(150 + 113 + 25 * (15 - i), 90 - (renderer.getCurrentFont().getCharacterHeight() / 2), "" + (i + 1));
|
||||||
}
|
}
|
||||||
for (int i = 7; i >= 0; i--) {
|
for (int i = 7; i >= 0; i--) {
|
||||||
if (pinsB[i] == 1) {
|
if (pinsB[i] == 1) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else if (pinsB[i] == 2) {
|
} else if (pinsB[i] == 2) {
|
||||||
colore(0.5f, 0.5f, 1.0f, 1.0f);
|
renderer.glColor4f(0.5f, 0.5f, 1.0f, 1.0f);
|
||||||
} else if (pinsB[i] == -1) {
|
} else if (pinsB[i] == -1) {
|
||||||
colore(0.7f, 0.7f, 0.7f, 1.0f);
|
renderer.glColor4f(0.7f, 0.7f, 0.7f, 1.0f);
|
||||||
} else if (pinsB[i] == 0) {
|
} else if (pinsB[i] == 0) {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(150+103+25*(i), 170, 20, 20);
|
renderer.glFillColor(150 + 103 + 25 * (i), 170, 20, 20);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(150+113+25*(i), 180-(PIDisplay.renderer.getCurrentFont().charH/2), ""+(i+1));
|
renderer.glDrawStringCenter(150 + 113 + 25 * (i), 180 - (renderer.getCurrentFont().getCharacterHeight() / 2), "" + (i + 1));
|
||||||
}
|
}
|
||||||
for (int i = 0; i < 8; i++) {
|
for (int i = 0; i < 8; i++) {
|
||||||
if (dataB[i]) {
|
if (dataB[i]) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else {
|
} else {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(150+160+10*(i), 150, 8, 8);
|
renderer.glFillColor(150 + 160 + 10 * (i), 150, 8, 8);
|
||||||
}
|
}
|
||||||
|
|
||||||
//GPIO
|
//GPIO
|
||||||
for (int i = 0; i < 40; i++) {
|
for (int i = 0; i < 40; i++) {
|
||||||
if (gpio[i] == true) {
|
if (gpio[i] == true) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else {
|
} else {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
if (i % 2 == 0) {
|
if (i % 2 == 0) {
|
||||||
PIDisplay.renderer.glFillRect(53+15*((i)/2), 50, 5, 5);
|
renderer.glFillColor(53 + 15 * ((i) / 2), 50, 5, 5);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(55+15*((i)/2), 60, ""+(i+1));
|
renderer.glDrawStringCenter(55 + 15 * ((i) / 2), 60, "" + (i + 1));
|
||||||
} else {
|
} else {
|
||||||
PIDisplay.renderer.glFillRect(53+15*((i-1)/2), 40, 5, 5);
|
renderer.glFillColor(53 + 15 * ((i - 1) / 2), 40, 5, 5);
|
||||||
colore(0.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 0.0f, 0.0f, 1.0f);
|
||||||
PIDisplay.renderer.glDrawStringCenter(55+15*((i-1)/2), 35-PIDisplay.renderer.getCurrentFont().charH, ""+(i+1));
|
renderer.glDrawStringCenter(55 + 15 * ((i - 1) / 2), 35 - renderer.getCurrentFont().getCharacterHeight(), "" + (i + 1));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -165,18 +163,18 @@ public class KeyboardDebugScreen extends Screen {
|
|||||||
for (int c = 0; c < 8; c++) {
|
for (int c = 0; c < 8; c++) {
|
||||||
for (int r = 0; r < 8; r++) {
|
for (int r = 0; r < 8; r++) {
|
||||||
if (ks[c][r]) {
|
if (ks[c][r]) {
|
||||||
colore(0.0f, 1.0f, 0.0f, 1.0f);
|
renderer.glColor4f(0.0f, 1.0f, 0.0f, 1.0f);
|
||||||
} else {
|
} else {
|
||||||
colore(1.0f, 0.0f, 0.0f, 1.0f);
|
renderer.glColor4f(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glFillRect(250+6*c, 250+6*r, 5, 5);
|
renderer.glFillColor(250 + 6 * c, 250 + 6 * r, 5, 5);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void beforeRender(float dt) {
|
public void beforeRender(float dt) {
|
||||||
if (System.currentTimeMillis()-beforetime >= 1000) {
|
if (System.currentTimeMillis() - beforetime >= 1000) {
|
||||||
keyevent = "NONE";
|
keyevent = "NONE";
|
||||||
keyX = 0;
|
keyX = 0;
|
||||||
keyY = 0;
|
keyY = 0;
|
||||||
@ -209,18 +207,17 @@ public class KeyboardDebugScreen extends Screen {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static int[] pinsA = new int[] { 2, 2, 2, 2, 2, 2, 2, 1, -1, -1, 0, 0, 0, 0, 2, -1 };
|
||||||
public static int[] pinsA = new int[]{2, 2, 2, 2, 2, 2, 2, 1, -1, -1, 0, 0, 0, 0, 2, -1};
|
public static int[] pinsB = new int[] { 0, 0, 2, 2, 2, 2, -1, 1, 0, -1, 2, 2, 2, 2, 0, -1 };
|
||||||
public static int[] pinsB = new int[]{0, 0, 2, 2, 2, 2, -1, 1, 0, -1, 2, 2, 2, 2, 0, -1};
|
|
||||||
public static boolean[] dataA = new boolean[8];
|
public static boolean[] dataA = new boolean[8];
|
||||||
public static boolean[] dataB = new boolean[8];
|
public static boolean[] dataB = new boolean[8];
|
||||||
public static boolean[][] ks = new boolean[8][8];
|
public static boolean[][] ks = new boolean[8][8];
|
||||||
public static boolean[] gpio = new boolean[40];
|
public static boolean[] gpio = new boolean[40];
|
||||||
|
|
||||||
public static void log(String str) {
|
public static void log(String str) {
|
||||||
String[] newlog = log;
|
final String[] newlog = log;
|
||||||
for (int i = 1; i < 5; i++) {
|
for (int i = 1; i < 5; i++) {
|
||||||
newlog[i-1] = newlog[i];
|
newlog[i - 1] = newlog[i];
|
||||||
}
|
}
|
||||||
newlog[4] = "[" + System.currentTimeMillis() + "]" + str;
|
newlog[4] = "[" + System.currentTimeMillis() + "]" + str;
|
||||||
log = newlog;
|
log = newlog;
|
||||||
|
@ -1,20 +1,20 @@
|
|||||||
package org.warp.picalculator.gui.screens;
|
package org.warp.picalculator.gui.screens;
|
||||||
|
|
||||||
import static org.warp.picalculator.gui.PIDisplay.colore;
|
import static org.warp.picalculator.gui.DisplayManager.colore;
|
||||||
import static org.warp.picalculator.gui.PIDisplay.fonts;
|
import static org.warp.picalculator.gui.DisplayManager.fonts;
|
||||||
|
|
||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
|
import org.warp.picalculator.gui.GraphicUtils;
|
||||||
|
|
||||||
public class LoadingScreen extends Screen {
|
public class LoadingScreen extends Screen {
|
||||||
|
|
||||||
public float endLoading;
|
public float endLoading;
|
||||||
boolean mustRefresh = true;
|
boolean mustRefresh = true;
|
||||||
public float loadingTextTranslation = 0.0f;
|
public float loadingTextTranslation = 0.0f;
|
||||||
public boolean loadingTextTranslationTopToBottom = true;
|
|
||||||
private boolean loading;
|
private boolean loading;
|
||||||
private static final String titleString = "PICalculator by Andrea Cavalli";
|
private static final String titleString = "Andrea Cavalli's Algebraic Calculator";
|
||||||
|
|
||||||
public LoadingScreen() {
|
public LoadingScreen() {
|
||||||
super();
|
super();
|
||||||
@ -27,52 +27,47 @@ public class LoadingScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() throws InterruptedException {
|
public void init() throws InterruptedException {}
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void beforeRender(float dt) {
|
public void beforeRender(float dt) {
|
||||||
if (loadingTextTranslation >= 10.0f) {
|
loadingTextTranslation = GraphicUtils.sinDeg(endLoading * 90f) * 10f;
|
||||||
loadingTextTranslation = 10.0f;
|
|
||||||
loadingTextTranslationTopToBottom = false;
|
|
||||||
} else if (loadingTextTranslation <= -10.0f) {
|
|
||||||
loadingTextTranslation = -10.0f;
|
|
||||||
loadingTextTranslationTopToBottom = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (loadingTextTranslationTopToBottom) {
|
|
||||||
loadingTextTranslation += dt * 15;
|
|
||||||
} else {
|
|
||||||
loadingTextTranslation -= dt * 15;
|
|
||||||
}
|
|
||||||
|
|
||||||
endLoading += dt;
|
endLoading += dt;
|
||||||
if (endLoading >= 2) {
|
if (endLoading >= 5f) {
|
||||||
loading = false;
|
loading = false;
|
||||||
PIDisplay.INSTANCE.setScreen(new MathInputScreen());
|
DisplayManager.INSTANCE.setScreen(new MathInputScreen());
|
||||||
}
|
}
|
||||||
mustRefresh = true;
|
mustRefresh = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void render() {
|
public void render() {
|
||||||
PIDisplay.renderer.glSetFont(fonts[2]);
|
fonts[2].use(DisplayManager.display);
|
||||||
colore(1.0f, 1.0f, 1.0f, 1.0f);
|
DisplayManager.renderer.glClearColor(0xFF000000);
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2) - 1,(int) ((Main.screenSize[1]/ 2) - 25 + loadingTextTranslation), titleString);
|
DisplayManager.renderer.glClear(DisplayManager.display.getWidth(), DisplayManager.display.getWidth());
|
||||||
colore(1.0f, 1.0f, 1.0f, 1.0f);
|
DisplayManager.renderer.glColor3i(230, 33, 23);
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2) + 1,(int) ((Main.screenSize[1]/ 2) - 25 + loadingTextTranslation), titleString);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) - 1, (int) ((Main.screenSize[1] / 2) - 25 + loadingTextTranslation), titleString);
|
||||||
colore(1.0f, 1.0f, 1.0f, 1.0f);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) - 2, (int) ((Main.screenSize[1] / 2) - 25 + loadingTextTranslation), titleString);
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1]/ 2) - 25 - 1 + loadingTextTranslation), titleString);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) + 1, (int) ((Main.screenSize[1] / 2) - 25 + loadingTextTranslation), titleString);
|
||||||
colore(1.0f, 1.0f, 1.0f, 1.0f);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) + 2, (int) ((Main.screenSize[1] / 2) - 25 + loadingTextTranslation), titleString);
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1]/ 2) - 25 + 1 + loadingTextTranslation), titleString);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1] / 2) - 25 - 1 + loadingTextTranslation), titleString);
|
||||||
colore(1.0f, 0.5f, 0.0f, 1.0f);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1] / 2) - 25 - 2 + loadingTextTranslation), titleString);
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1]/ 2) - 25 + loadingTextTranslation), titleString);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1] / 2) - 25 + 1 + loadingTextTranslation), titleString);
|
||||||
colore(0.0f, 0.0f, 0.0f, 0.75f);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1] / 2) - 25 + 2 + loadingTextTranslation), titleString);
|
||||||
PIDisplay.renderer.glSetFont(fonts[0]);
|
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (Main.screenSize[1]/ 2) + 11, "LOADING");
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) + 1, (int) ((Main.screenSize[1] / 2) - 25 + 1 + loadingTextTranslation), titleString);
|
||||||
PIDisplay.renderer.glSetFont(fonts[1]);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) - 1, (int) ((Main.screenSize[1] / 2) - 25 + 1 + loadingTextTranslation), titleString);
|
||||||
colore(0.0f, 0.0f, 0.0f, 0.5f);
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) - 1, (int) ((Main.screenSize[1] / 2) - 25 - 1 + loadingTextTranslation), titleString);
|
||||||
PIDisplay.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (Main.screenSize[1]/ 2) + 22, "PLEASE WAIT...");
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2) + 1, (int) ((Main.screenSize[1] / 2) - 25 - 1 + loadingTextTranslation), titleString);
|
||||||
|
DisplayManager.renderer.glColor3i(255, 255, 255);
|
||||||
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (int) ((Main.screenSize[1] / 2) - 25 + loadingTextTranslation), titleString);
|
||||||
|
DisplayManager.renderer.glColor4f(0.0f, 0.0f, 0.0f, 0.75f);
|
||||||
|
fonts[0].use(DisplayManager.display);
|
||||||
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (Main.screenSize[1] / 2) + 11, "LOADING");
|
||||||
|
fonts[1].use(DisplayManager.display);
|
||||||
|
DisplayManager.renderer.glColor4f(0.0f, 0.0f, 0.0f, 0.5f);
|
||||||
|
DisplayManager.renderer.glDrawStringCenter((Main.screenSize[0] / 2), (Main.screenSize[1] / 2) + 22, "PLEASE WAIT...");
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,17 +8,16 @@ import javax.imageio.ImageIO;
|
|||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
import org.warp.picalculator.device.Keyboard;
|
import org.warp.picalculator.device.Keyboard;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.RAWSkin;
|
||||||
|
|
||||||
public class MarioScreen extends Screen {
|
public class MarioScreen extends Screen {
|
||||||
|
|
||||||
private int[] skin;
|
private RAWSkin skin;
|
||||||
private int[] skinSize;
|
private RAWSkin groundskin;
|
||||||
private int[] ground;
|
|
||||||
private int[] groundSize;
|
|
||||||
private boolean errored;
|
private boolean errored;
|
||||||
public float[] marioPos = new float[]{30,0};
|
public float[] marioPos = new float[] { 30, 0 };
|
||||||
public float[] marioForces = new float[]{0,0};
|
public float[] marioForces = new float[] { 0, 0 };
|
||||||
public float walkAnimation = 0;
|
public float walkAnimation = 0;
|
||||||
public float jumptime = 0;
|
public float jumptime = 0;
|
||||||
public boolean walking = false;
|
public boolean walking = false;
|
||||||
@ -26,7 +25,7 @@ public class MarioScreen extends Screen {
|
|||||||
public boolean jumping = false;
|
public boolean jumping = false;
|
||||||
public boolean flipped = false;
|
public boolean flipped = false;
|
||||||
public boolean onGround = true;
|
public boolean onGround = true;
|
||||||
public int[] marioSkinPos = new int[]{0,0};
|
public int[] marioSkinPos = new int[] { 0, 0 };
|
||||||
|
|
||||||
public MarioScreen() {
|
public MarioScreen() {
|
||||||
super();
|
super();
|
||||||
@ -35,22 +34,11 @@ public class MarioScreen extends Screen {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() {
|
public void init() {
|
||||||
BufferedImage img;
|
|
||||||
try {
|
try {
|
||||||
img = ImageIO.read(Main.instance.getClass().getResource("/marioskin.png"));
|
skin = DisplayManager.display.loadSkin("marioskin.png");
|
||||||
skin = PIDisplay.renderer.getMatrixOfImage(img);
|
groundskin = DisplayManager.display.loadSkin("marioground.png");
|
||||||
skinSize = new int[] { img.getWidth(), img.getHeight() };
|
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
errored = true;
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
img = ImageIO.read(Main.instance.getClass().getResource("/marioground.png"));
|
|
||||||
ground = PIDisplay.renderer.getMatrixOfImage(img);
|
|
||||||
groundSize = new int[] { img.getWidth(), img.getHeight() };
|
|
||||||
} catch (IOException e) {
|
|
||||||
e.printStackTrace();
|
|
||||||
errored = true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -65,36 +53,36 @@ public class MarioScreen extends Screen {
|
|||||||
public void beforeRender(float dt) {
|
public void beforeRender(float dt) {
|
||||||
if (!errored) {
|
if (!errored) {
|
||||||
walkAnimation += dt;
|
walkAnimation += dt;
|
||||||
boolean rightPressed = Keyboard.isKeyDown(2, 5);
|
final boolean rightPressed = Keyboard.isKeyDown(2, 5);
|
||||||
boolean leftPressed = Keyboard.isKeyDown(2, 3);
|
final boolean leftPressed = Keyboard.isKeyDown(2, 3);
|
||||||
boolean jumpPressed = Keyboard.isKeyDown(2, 1);
|
final boolean jumpPressed = Keyboard.isKeyDown(2, 1);
|
||||||
if ((leftPressed || rightPressed) == (leftPressed & rightPressed)) {
|
if ((leftPressed || rightPressed) == (leftPressed & rightPressed)) {
|
||||||
walking = false;
|
walking = false;
|
||||||
walkAnimation = 0;
|
walkAnimation = 0;
|
||||||
} else {
|
} else {
|
||||||
if (rightPressed) { //RIGHT
|
if (rightPressed) { //RIGHT
|
||||||
if (marioForces[0] < 500f) {
|
if (marioForces[0] < 500f) {
|
||||||
marioForces[0] += dt*500f;
|
marioForces[0] += dt * 500f;
|
||||||
}
|
}
|
||||||
walking = true;
|
walking = true;
|
||||||
flipped = false;
|
flipped = false;
|
||||||
}
|
}
|
||||||
if (leftPressed) { //LEFT
|
if (leftPressed) { //LEFT
|
||||||
if (marioForces[0] > -500f) {
|
if (marioForces[0] > -500f) {
|
||||||
marioForces[0] -= dt*500f;
|
marioForces[0] -= dt * 500f;
|
||||||
}
|
}
|
||||||
walking = true;
|
walking = true;
|
||||||
flipped = true;
|
flipped = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (jumpPressed) { //JUMP
|
if (jumpPressed) { //JUMP
|
||||||
jumptime+=dt;
|
jumptime += dt;
|
||||||
if (!jumping && onGround) {
|
if (!jumping && onGround) {
|
||||||
marioForces[1] = dt*(4*1569.6f);
|
marioForces[1] = dt * (4 * 1569.6f);
|
||||||
jumping = true;
|
jumping = true;
|
||||||
onGround = false;
|
onGround = false;
|
||||||
} else if (jumptime <= 0.5f) {
|
} else if (jumptime <= 0.5f) {
|
||||||
marioForces[1] = dt*(4*1569.6f);
|
marioForces[1] = dt * (4 * 1569.6f);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
jumping = false;
|
jumping = false;
|
||||||
@ -104,7 +92,7 @@ public class MarioScreen extends Screen {
|
|||||||
marioSkinPos[0] = 0;
|
marioSkinPos[0] = 0;
|
||||||
marioSkinPos[1] = 0;
|
marioSkinPos[1] = 0;
|
||||||
} else if (onGround & walking & !running & !jumping && walkAnimation >= 0.08) {
|
} else if (onGround & walking & !running & !jumping && walkAnimation >= 0.08) {
|
||||||
while(walkAnimation > 0.08) {
|
while (walkAnimation > 0.08) {
|
||||||
walkAnimation -= 0.08;
|
walkAnimation -= 0.08;
|
||||||
if (marioSkinPos[0] == 1 & marioSkinPos[1] == 0) {
|
if (marioSkinPos[0] == 1 & marioSkinPos[1] == 0) {
|
||||||
marioSkinPos[0] += 2;
|
marioSkinPos[0] += 2;
|
||||||
@ -121,41 +109,43 @@ public class MarioScreen extends Screen {
|
|||||||
marioSkinPos[0] = 5;
|
marioSkinPos[0] = 5;
|
||||||
marioSkinPos[1] = 1;
|
marioSkinPos[1] = 1;
|
||||||
}
|
}
|
||||||
marioForces[1] -= dt*1569.6;
|
marioForces[1] -= dt * 1569.6;
|
||||||
marioPos[0] += dt*marioForces[0];
|
marioPos[0] += dt * marioForces[0];
|
||||||
if (!onGround) {
|
if (!onGround) {
|
||||||
marioPos[1] -= dt*marioForces[1];
|
marioPos[1] -= dt * marioForces[1];
|
||||||
}
|
}
|
||||||
marioForces[0] *= 0.75;
|
marioForces[0] *= 0.75;
|
||||||
|
|
||||||
PIDisplay.renderer.glClearColor(0xff9290ff);
|
DisplayManager.renderer.glClearColor(0xff9290ff);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void render() {
|
public void render() {
|
||||||
if (errored) {
|
if (errored) {
|
||||||
PIDisplay.renderer.glDrawStringLeft(0, 20, "ERROR");
|
DisplayManager.renderer.glDrawStringLeft(0, 20, "ERROR");
|
||||||
} else {
|
} else {
|
||||||
PIDisplay.renderer.glSetFont(PIDisplay.fonts[0]);
|
DisplayManager.fonts[0].use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 0, 25+25, 0, 0, 16, 16, false);
|
groundskin.use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 0, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*2, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 1, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*3, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 2, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*4, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 3, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*5, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 4, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*6, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 5, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*7, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 6, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*8, 25+25, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 7, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 0, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 8, 25 + 25, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16, 25+25+16, 0, 0, 16, 16, false);
|
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*2, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 0, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*3, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 1, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*4, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 2, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*5, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 3, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*6, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 4, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*7, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 5, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
PIDisplay.renderer.glDrawSkin(groundSize[0], ground, 16*8, 25+25+16, 0, 0, 16, 16, false);
|
DisplayManager.renderer.glFillRect(16 * 6, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
|
DisplayManager.renderer.glFillRect(16 * 7, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
|
DisplayManager.renderer.glFillRect(16 * 8, 25 + 25 + 16 * 1, 16, 16, 0, 0, 16, 16);
|
||||||
|
|
||||||
// EASTER EGG
|
// EASTER EGG
|
||||||
// glSetFont(PIDisplay.fonts[4]);
|
// glSetFont(PIDisplay.fonts[4]);
|
||||||
@ -175,7 +165,9 @@ public class MarioScreen extends Screen {
|
|||||||
// glDrawStringRight(0, Main.screenSize[1]-glGetCurrentFontHeight(), "G");
|
// glDrawStringRight(0, Main.screenSize[1]-glGetCurrentFontHeight(), "G");
|
||||||
|
|
||||||
//DRAW MARIO
|
//DRAW MARIO
|
||||||
PIDisplay.renderer.glDrawSkin(skinSize[0], skin, getPosX()-18, 25+getPosY(), 35*(marioSkinPos[0]+(flipped?2:1)), 27*marioSkinPos[1], 35*(marioSkinPos[0]+(flipped?1:2)), 27*(marioSkinPos[1]+1), true);
|
skin.use(DisplayManager.display);
|
||||||
|
DisplayManager.renderer.glFillRect(getPosX() - 18, 25 + getPosY(), 35, 27, 35 * (marioSkinPos[0] + 1), 27 * marioSkinPos[1], 35, 27);
|
||||||
|
// PIDisplay.renderer.glDrawSkin(getPosX() - 18, 25 + getPosY(), 35 * (marioSkinPos[0] + (flipped ? 2 : 1)), 27 * marioSkinPos[1], 35 * (marioSkinPos[0] + (flipped ? 1 : 2)), 27 * (marioSkinPos[1] + 1), true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -195,11 +187,11 @@ public class MarioScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private int getPosX() {
|
private int getPosX() {
|
||||||
return (int)marioPos[0];
|
return (int) marioPos[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
private int getPosY() {
|
private int getPosY() {
|
||||||
return (int)marioPos[1];
|
return (int) marioPos[1];
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -15,8 +15,9 @@ import org.warp.picalculator.Main;
|
|||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.device.Keyboard;
|
import org.warp.picalculator.device.Keyboard;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
|
import org.warp.picalculator.gui.graphicengine.Renderer;
|
||||||
import org.warp.picalculator.math.AngleMode;
|
import org.warp.picalculator.math.AngleMode;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
@ -114,7 +115,7 @@ public class MathInputScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void interpreta(boolean temporary) throws Error {
|
public void interpreta(boolean temporary) throws Error {
|
||||||
String eqn = nuovaEquazione;
|
final String eqn = nuovaEquazione;
|
||||||
if (!temporary) {
|
if (!temporary) {
|
||||||
equazioneCorrente = eqn;
|
equazioneCorrente = eqn;
|
||||||
}
|
}
|
||||||
@ -134,10 +135,10 @@ public class MathInputScreen extends Screen {
|
|||||||
caretPos = nuovaEquazione.length();
|
caretPos = nuovaEquazione.length();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (PIDisplay.error == null) {
|
if (DisplayManager.error == null) {
|
||||||
PIDisplay.renderer.glClearColor(0xFFc5c2af);
|
DisplayManager.renderer.glClearColor(0xFFc5c2af);
|
||||||
} else {
|
} else {
|
||||||
PIDisplay.renderer.glClearColor(0xFFDC3C32);
|
DisplayManager.renderer.glClearColor(0xFFDC3C32);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -145,28 +146,28 @@ public class MathInputScreen extends Screen {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void renderStatusbar() {
|
public void renderStatusbar() {
|
||||||
PIDisplay.renderer.glColor3i(0, 0, 0);
|
Renderer renderer = DisplayManager.renderer;
|
||||||
int pos = 2;
|
renderer.glColor3f(1, 1, 1);
|
||||||
int spacersNumb = 1;
|
final int pos = 2;
|
||||||
|
final int spacersNumb = 1;
|
||||||
int skinN = 0;
|
int skinN = 0;
|
||||||
if (calc.exactMode) {
|
if (calc.exactMode) {
|
||||||
skinN = 22;
|
skinN = 22;
|
||||||
PIDisplay.drawSkinPart(2 + 18 * pos + 2 * spacersNumb, 2, 16 * skinN, 16 * 0, 16 + 16 * skinN, 16 + 16 * 0);
|
|
||||||
} else {
|
} else {
|
||||||
skinN = 21;
|
skinN = 21;
|
||||||
PIDisplay.drawSkinPart(2 + 18 * pos + 2 * spacersNumb, 2, 16 * skinN, 16 * 0, 16 + 16 * skinN, 16 + 16 * 0);
|
|
||||||
}
|
}
|
||||||
|
renderer.glFillRect(2 + 18 * pos + 2 * spacersNumb, 2, 16, 16, 16 * skinN, 16 * 0, 16, 16);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void render() {
|
public void render() {
|
||||||
PIDisplay.renderer.glSetFont(fontBig);
|
fontBig.use(DisplayManager.display);
|
||||||
final int textColor = 0xFF000000;
|
final int textColor = 0xFF000000;
|
||||||
final int padding = 4;
|
final int padding = 4;
|
||||||
PIDisplay.renderer.glColor(textColor);
|
DisplayManager.renderer.glColor(textColor);
|
||||||
final int caretRealPos = MathematicalSymbols.getGraphicRepresentation(nuovaEquazione.substring(0, caretPos)).length()*(fontBig.charW+1);
|
final int caretRealPos = MathematicalSymbols.getGraphicRepresentation(nuovaEquazione.substring(0, caretPos)).length() * (fontBig.getCharacterWidth() + 1);
|
||||||
final String inputTextWithoutCaret = MathematicalSymbols.getGraphicRepresentation(nuovaEquazione);
|
final String inputTextWithoutCaret = MathematicalSymbols.getGraphicRepresentation(nuovaEquazione);
|
||||||
final boolean tooLongI = padding+PIDisplay.renderer.glGetStringWidth(fontBig, nuovaEquazione)+padding >= Main.screenSize[0];
|
final boolean tooLongI = padding + fontBig.getStringWidth(nuovaEquazione) + padding >= Main.screenSize[0];
|
||||||
int scrollI = 0;
|
int scrollI = 0;
|
||||||
if (tooLongI) {
|
if (tooLongI) {
|
||||||
scrollI = -scrollX;
|
scrollI = -scrollX;
|
||||||
@ -176,23 +177,23 @@ public class MathInputScreen extends Screen {
|
|||||||
scrollI = 0;
|
scrollI = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glDrawStringLeft(padding+scrollI, padding+20, inputTextWithoutCaret);
|
DisplayManager.renderer.glDrawStringLeft(padding + scrollI, padding + 20, inputTextWithoutCaret);
|
||||||
if (showCaret) {
|
if (showCaret) {
|
||||||
PIDisplay.renderer.glDrawStringLeft(padding+scrollI+caretRealPos, padding+20, "|");
|
DisplayManager.renderer.glDrawStringLeft(padding + scrollI + caretRealPos, padding + 20, "|");
|
||||||
}
|
}
|
||||||
if (tooLongI) {
|
if (tooLongI) {
|
||||||
PIDisplay.renderer.glColor(PIDisplay.renderer.glGetClearColor());
|
DisplayManager.renderer.glColor(DisplayManager.renderer.glGetClearColor());
|
||||||
PIDisplay.renderer.glFillRect(Main.screenSize[0]-16-2, padding+20, fontBig.charH, Main.screenSize[0]);
|
DisplayManager.renderer.glFillColor(Main.screenSize[0] - 16 - 2, padding + 20, fontBig.getCharacterHeight(), Main.screenSize[0]);
|
||||||
PIDisplay.renderer.glColor(textColor);
|
DisplayManager.renderer.glColor(textColor);
|
||||||
PIDisplay.drawSkinPart(Main.screenSize[0]-16, padding+20+fontBig.charH/2-16/2, 304, 0, 304+16, 16);
|
DisplayManager.drawSkinPart(Main.screenSize[0] - 16, padding + 20 + fontBig.getCharacterHeight() / 2 - 16 / 2, 304, 0, 304 + 16, 16);
|
||||||
}
|
}
|
||||||
if (calc.f != null) {
|
if (calc.f != null) {
|
||||||
int topSpacing = 0;
|
int topSpacing = 0;
|
||||||
Iterator<Function> iter = calc.f.iterator();
|
final Iterator<Function> iter = calc.f.iterator();
|
||||||
while (iter.hasNext()) {
|
while (iter.hasNext()) {
|
||||||
Function fnc = iter.next();
|
final Function fnc = iter.next();
|
||||||
try {
|
try {
|
||||||
final boolean tooLong = padding+fnc.getWidth()+padding >= Main.screenSize[0];
|
final boolean tooLong = padding + fnc.getWidth() + padding >= Main.screenSize[0];
|
||||||
int scrollA = 0;
|
int scrollA = 0;
|
||||||
if (tooLong) {
|
if (tooLong) {
|
||||||
scrollA = -scrollX;
|
scrollA = -scrollX;
|
||||||
@ -202,15 +203,15 @@ public class MathInputScreen extends Screen {
|
|||||||
scrollA = 0;
|
scrollA = 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
final int y = padding+20+padding+fontBig.charH+1+topSpacing;
|
final int y = padding + 20 + padding + fontBig.getCharacterHeight() + 1 + topSpacing;
|
||||||
fnc.draw(padding+scrollA, y);
|
fnc.draw(padding + scrollA, y);
|
||||||
if (tooLong) {
|
if (tooLong) {
|
||||||
PIDisplay.renderer.glColor(PIDisplay.renderer.glGetClearColor());
|
DisplayManager.renderer.glColor(DisplayManager.renderer.glGetClearColor());
|
||||||
PIDisplay.renderer.glFillRect(Main.screenSize[0]-16-2, y, fnc.getHeight(), Main.screenSize[0]);
|
DisplayManager.renderer.glFillColor(Main.screenSize[0] - 16 - 2, y, fnc.getHeight(), Main.screenSize[0]);
|
||||||
PIDisplay.renderer.glColor(textColor);
|
DisplayManager.renderer.glColor(textColor);
|
||||||
PIDisplay.drawSkinPart(Main.screenSize[0]-16, y+fnc.getHeight()/2-16/2, 304, 0, 304+16, 16);
|
DisplayManager.drawSkinPart(Main.screenSize[0] - 16, y + fnc.getHeight() / 2 - 16 / 2, 304, 0, 304 + 16, 16);
|
||||||
}
|
}
|
||||||
} catch (NullPointerException e) {
|
} catch (final NullPointerException e) {
|
||||||
iter.remove();
|
iter.remove();
|
||||||
}
|
}
|
||||||
topSpacing += fnc.getHeight() + 2;
|
topSpacing += fnc.getHeight() + 2;
|
||||||
@ -218,16 +219,16 @@ public class MathInputScreen extends Screen {
|
|||||||
}
|
}
|
||||||
if (calc.f2 != null) {
|
if (calc.f2 != null) {
|
||||||
int bottomSpacing = 0;
|
int bottomSpacing = 0;
|
||||||
for (Function f : calc.f2) {
|
for (final Function f : calc.f2) {
|
||||||
bottomSpacing += f.getHeight()+2;
|
bottomSpacing += f.getHeight() + 2;
|
||||||
f.draw(PIDisplay.display.getWidth() - 2 - f.getWidth(), PIDisplay.display.getHeight() - bottomSpacing);
|
f.draw(DisplayManager.display.getWidth() - 2 - f.getWidth(), DisplayManager.display.getHeight() - bottomSpacing);
|
||||||
}
|
}
|
||||||
if (calc.resultsCount > 1 && calc.resultsCount != calc.f2.size()) {
|
if (calc.resultsCount > 1 && calc.resultsCount != calc.f2.size()) {
|
||||||
String resultsCountText = calc.resultsCount+" total results".toUpperCase();
|
final String resultsCountText = calc.resultsCount + " total results".toUpperCase();
|
||||||
PIDisplay.renderer.glColor(0xFF9AAEA0);
|
DisplayManager.renderer.glColor(0xFF9AAEA0);
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(true));
|
Utils.getFont(true).use(DisplayManager.display);
|
||||||
bottomSpacing += fontBig.charH+2;
|
bottomSpacing += fontBig.getCharacterHeight() + 2;
|
||||||
PIDisplay.renderer.glDrawStringRight(PIDisplay.display.getWidth() - 2, PIDisplay.display.getHeight() - bottomSpacing, resultsCountText);
|
DisplayManager.renderer.glDrawStringRight(DisplayManager.display.getWidth() - 2, DisplayManager.display.getHeight() - bottomSpacing, resultsCountText);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -251,26 +252,24 @@ public class MathInputScreen extends Screen {
|
|||||||
try {
|
try {
|
||||||
try {
|
try {
|
||||||
interpreta(true);
|
interpreta(true);
|
||||||
showVariablesDialog(new Runnable(){
|
showVariablesDialog(() -> {
|
||||||
@Override
|
equazioneCorrente = nuovaEquazione;
|
||||||
public void run() {
|
calc.f2 = calc.f;
|
||||||
equazioneCorrente = nuovaEquazione;
|
afterDoNextStep = true;
|
||||||
calc.f2 = calc.f;
|
simplify(MathInputScreen.this);
|
||||||
afterDoNextStep = true;
|
|
||||||
simplify(MathInputScreen.this);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
} catch (Exception ex) {
|
} catch (final Exception ex) {
|
||||||
if (Utils.debugOn)
|
if (Utils.debugOn) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
|
}
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
StringWriter sw = new StringWriter();
|
final StringWriter sw = new StringWriter();
|
||||||
PrintWriter pw = new PrintWriter(sw);
|
final PrintWriter pw = new PrintWriter(sw);
|
||||||
e.printStackTrace(pw);
|
e.printStackTrace(pw);
|
||||||
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
||||||
PIDisplay.error = e.id.toString();
|
DisplayManager.error = e.id.toString();
|
||||||
System.err.println(e.id);
|
System.err.println(e.id);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -279,10 +278,10 @@ public class MathInputScreen extends Screen {
|
|||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
case SOLVE:
|
case SOLVE:
|
||||||
if (PIDisplay.error != null) {
|
if (DisplayManager.error != null) {
|
||||||
Utils.debug.println("Resetting after error...");
|
Utils.debug.println("Resetting after error...");
|
||||||
PIDisplay.error = null;
|
DisplayManager.error = null;
|
||||||
this.equazioneCorrente = null;
|
equazioneCorrente = null;
|
||||||
calc.f = null;
|
calc.f = null;
|
||||||
calc.f2 = null;
|
calc.f2 = null;
|
||||||
calc.resultsCount = 0;
|
calc.resultsCount = 0;
|
||||||
@ -296,26 +295,24 @@ public class MathInputScreen extends Screen {
|
|||||||
if (nuovaEquazione != equazioneCorrente && nuovaEquazione.length() > 0) {
|
if (nuovaEquazione != equazioneCorrente && nuovaEquazione.length() > 0) {
|
||||||
changeEquationScreen();
|
changeEquationScreen();
|
||||||
interpreta(true);
|
interpreta(true);
|
||||||
showVariablesDialog(new Runnable(){
|
showVariablesDialog(() -> {
|
||||||
@Override
|
equazioneCorrente = nuovaEquazione;
|
||||||
public void run() {
|
solve();
|
||||||
equazioneCorrente = nuovaEquazione;
|
});
|
||||||
solve();
|
|
||||||
}});
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (final Exception ex) {
|
||||||
if (Utils.debugOn) {
|
if (Utils.debugOn) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
StringWriter sw = new StringWriter();
|
final StringWriter sw = new StringWriter();
|
||||||
PrintWriter pw = new PrintWriter(sw);
|
final PrintWriter pw = new PrintWriter(sw);
|
||||||
e.printStackTrace(pw);
|
e.printStackTrace(pw);
|
||||||
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
||||||
PIDisplay.error = e.id.toString();
|
DisplayManager.error = e.id.toString();
|
||||||
System.err.println(e.id);
|
System.err.println(e.id);
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
@ -384,7 +381,7 @@ public class MathInputScreen extends Screen {
|
|||||||
typeChar("√");
|
typeChar("√");
|
||||||
return true;
|
return true;
|
||||||
case POWER_OF_2:
|
case POWER_OF_2:
|
||||||
typeChar(MathematicalSymbols.POWER+"2");
|
typeChar(MathematicalSymbols.POWER + "2");
|
||||||
return true;
|
return true;
|
||||||
case POWER_OF_x:
|
case POWER_OF_x:
|
||||||
typeChar(MathematicalSymbols.POWER);
|
typeChar(MathematicalSymbols.POWER);
|
||||||
@ -419,12 +416,14 @@ public class MathInputScreen extends Screen {
|
|||||||
case DELETE:
|
case DELETE:
|
||||||
if (nuovaEquazione.length() > 0) {
|
if (nuovaEquazione.length() > 0) {
|
||||||
if (caretPos > 0) {
|
if (caretPos > 0) {
|
||||||
caretPos-=1;
|
caretPos -= 1;
|
||||||
nuovaEquazione=nuovaEquazione.substring(0, caretPos)+nuovaEquazione.substring(caretPos+1, nuovaEquazione.length());
|
nuovaEquazione = nuovaEquazione.substring(0, caretPos) + nuovaEquazione.substring(caretPos + 1, nuovaEquazione.length());
|
||||||
} else {
|
} else {
|
||||||
nuovaEquazione = nuovaEquazione.substring(1);
|
nuovaEquazione = nuovaEquazione.substring(1);
|
||||||
}
|
}
|
||||||
try {interpreta(true);} catch (Error e) {}
|
try {
|
||||||
|
interpreta(true);
|
||||||
|
} catch (final Error e) {}
|
||||||
}
|
}
|
||||||
afterDoNextStep = false;
|
afterDoNextStep = false;
|
||||||
return true;
|
return true;
|
||||||
@ -434,7 +433,7 @@ public class MathInputScreen extends Screen {
|
|||||||
} else {
|
} else {
|
||||||
caretPos = nuovaEquazione.length();
|
caretPos = nuovaEquazione.length();
|
||||||
}
|
}
|
||||||
scrollX = PIDisplay.renderer.glGetStringWidth(fontBig, nuovaEquazione.substring(0, caretPos)+"|||");
|
scrollX = fontBig.getStringWidth(nuovaEquazione.substring(0, caretPos) + "|||");
|
||||||
showCaret = true;
|
showCaret = true;
|
||||||
showCaretDelta = 0L;
|
showCaretDelta = 0L;
|
||||||
return true;
|
return true;
|
||||||
@ -444,18 +443,18 @@ public class MathInputScreen extends Screen {
|
|||||||
} else {
|
} else {
|
||||||
caretPos = 0;
|
caretPos = 0;
|
||||||
}
|
}
|
||||||
scrollX = PIDisplay.renderer.glGetStringWidth(fontBig, nuovaEquazione.substring(0, caretPos)+"|||");
|
scrollX = fontBig.getStringWidth(nuovaEquazione.substring(0, caretPos) + "|||");
|
||||||
showCaret = true;
|
showCaret = true;
|
||||||
showCaretDelta = 0L;
|
showCaretDelta = 0L;
|
||||||
return true;
|
return true;
|
||||||
case RESET:
|
case RESET:
|
||||||
if (PIDisplay.error != null) {
|
if (DisplayManager.error != null) {
|
||||||
Utils.debug.println("Resetting after error...");
|
Utils.debug.println("Resetting after error...");
|
||||||
PIDisplay.error = null;
|
DisplayManager.error = null;
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
caretPos = 0;
|
caretPos = 0;
|
||||||
nuovaEquazione="";
|
nuovaEquazione = "";
|
||||||
afterDoNextStep = false;
|
afterDoNextStep = false;
|
||||||
if (calc.f != null) {
|
if (calc.f != null) {
|
||||||
calc.f.clear();
|
calc.f.clear();
|
||||||
@ -472,27 +471,25 @@ public class MathInputScreen extends Screen {
|
|||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
case debug1:
|
case debug1:
|
||||||
PIDisplay.INSTANCE.setScreen(new EmptyScreen());
|
DisplayManager.INSTANCE.setScreen(new EmptyScreen());
|
||||||
return true;
|
return true;
|
||||||
case HISTORY_BACK:
|
case HISTORY_BACK:
|
||||||
if (PIDisplay.INSTANCE.canGoBack()) {
|
if (DisplayManager.INSTANCE.canGoBack()) {
|
||||||
if (equazioneCorrente != null && equazioneCorrente.length() > 0 & PIDisplay.sessions[PIDisplay.currentSession+1] instanceof MathInputScreen) {
|
if (equazioneCorrente != null && equazioneCorrente.length() > 0 & DisplayManager.sessions[DisplayManager.currentSession + 1] instanceof MathInputScreen) {
|
||||||
nuovaEquazione = equazioneCorrente;
|
nuovaEquazione = equazioneCorrente;
|
||||||
try {
|
try {
|
||||||
interpreta(true);
|
interpreta(true);
|
||||||
} catch (Error e) {
|
} catch (final Error e) {}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
case HISTORY_FORWARD:
|
case HISTORY_FORWARD:
|
||||||
if (PIDisplay.INSTANCE.canGoForward()) {
|
if (DisplayManager.INSTANCE.canGoForward()) {
|
||||||
if (equazioneCorrente != null && equazioneCorrente.length() > 0 & PIDisplay.sessions[PIDisplay.currentSession-1] instanceof MathInputScreen) {
|
if (equazioneCorrente != null && equazioneCorrente.length() > 0 & DisplayManager.sessions[DisplayManager.currentSession - 1] instanceof MathInputScreen) {
|
||||||
nuovaEquazione = equazioneCorrente;
|
nuovaEquazione = equazioneCorrente;
|
||||||
try {
|
try {
|
||||||
interpreta(true);
|
interpreta(true);
|
||||||
} catch (Error e) {
|
} catch (final Error e) {}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
@ -532,18 +529,18 @@ public class MathInputScreen extends Screen {
|
|||||||
try {
|
try {
|
||||||
try {
|
try {
|
||||||
return calc.solveExpression(f22);
|
return calc.solveExpression(f22);
|
||||||
} catch (Exception ex) {
|
} catch (final Exception ex) {
|
||||||
if (Utils.debugOn) {
|
if (Utils.debugOn) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
StringWriter sw = new StringWriter();
|
final StringWriter sw = new StringWriter();
|
||||||
PrintWriter pw = new PrintWriter(sw);
|
final PrintWriter pw = new PrintWriter(sw);
|
||||||
e.printStackTrace(pw);
|
e.printStackTrace(pw);
|
||||||
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
||||||
PIDisplay.error = e.id.toString();
|
DisplayManager.error = e.id.toString();
|
||||||
System.err.println(e.id);
|
System.err.println(e.id);
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
@ -554,15 +551,15 @@ public class MathInputScreen extends Screen {
|
|||||||
try {
|
try {
|
||||||
showVariablesDialog();
|
showVariablesDialog();
|
||||||
ArrayList<Function> results = new ArrayList<>();
|
ArrayList<Function> results = new ArrayList<>();
|
||||||
ArrayList<Function> partialResults = new ArrayList<>();
|
final ArrayList<Function> partialResults = new ArrayList<>();
|
||||||
for (Function f : calc.f2) {
|
for (final Function f : calc.f2) {
|
||||||
if (f instanceof Equation) {
|
if (f instanceof Equation) {
|
||||||
PIDisplay.INSTANCE.setScreen(new SolveEquationScreen(this));
|
DisplayManager.INSTANCE.setScreen(new SolveEquationScreen(this));
|
||||||
} else {
|
} else {
|
||||||
results.add(f);
|
results.add(f);
|
||||||
for (Function itm : results) {
|
for (final Function itm : results) {
|
||||||
if (itm.isSolved() == false) {
|
if (itm.isSolved() == false) {
|
||||||
List<Function> dt = itm.solveOneStep();
|
final List<Function> dt = itm.solveOneStep();
|
||||||
partialResults.addAll(dt);
|
partialResults.addAll(dt);
|
||||||
} else {
|
} else {
|
||||||
partialResults.add(itm);
|
partialResults.add(itm);
|
||||||
@ -579,27 +576,27 @@ public class MathInputScreen extends Screen {
|
|||||||
calc.resultsCount = results.size();
|
calc.resultsCount = results.size();
|
||||||
Collections.reverse(results);
|
Collections.reverse(results);
|
||||||
// add elements to al, including duplicates
|
// add elements to al, including duplicates
|
||||||
Set<Function> hs = new LinkedHashSet<>();
|
final Set<Function> hs = new LinkedHashSet<>();
|
||||||
hs.addAll(results);
|
hs.addAll(results);
|
||||||
results.clear();
|
results.clear();
|
||||||
results.addAll(hs);
|
results.addAll(hs);
|
||||||
calc.f2 = results;
|
calc.f2 = results;
|
||||||
for (Function rf : calc.f2) {
|
for (final Function rf : calc.f2) {
|
||||||
rf.generateGraphics();
|
rf.generateGraphics();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (final Exception ex) {
|
||||||
if (Utils.debugOn) {
|
if (Utils.debugOn) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
StringWriter sw = new StringWriter();
|
final StringWriter sw = new StringWriter();
|
||||||
PrintWriter pw = new PrintWriter(sw);
|
final PrintWriter pw = new PrintWriter(sw);
|
||||||
e.printStackTrace(pw);
|
e.printStackTrace(pw);
|
||||||
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
||||||
PIDisplay.error = e.id.toString();
|
DisplayManager.error = e.id.toString();
|
||||||
System.err.println(e.id);
|
System.err.println(e.id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -607,71 +604,72 @@ public class MathInputScreen extends Screen {
|
|||||||
protected void solve() {
|
protected void solve() {
|
||||||
try {
|
try {
|
||||||
try {
|
try {
|
||||||
for (Function f : calc.f) {
|
for (final Function f : calc.f) {
|
||||||
if (f instanceof Equation) {
|
if (f instanceof Equation) {
|
||||||
PIDisplay.INSTANCE.setScreen(new SolveEquationScreen(this));
|
DisplayManager.INSTANCE.setScreen(new SolveEquationScreen(this));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ArrayList<Function> results = solveExpression(calc.f);
|
final ArrayList<Function> results = solveExpression(calc.f);
|
||||||
if (results.size() == 0) {
|
if (results.size() == 0) {
|
||||||
calc.resultsCount = 0;
|
calc.resultsCount = 0;
|
||||||
} else {
|
} else {
|
||||||
calc.resultsCount = results.size();
|
calc.resultsCount = results.size();
|
||||||
Collections.reverse(results);
|
Collections.reverse(results);
|
||||||
// add elements to al, including duplicates
|
// add elements to al, including duplicates
|
||||||
Set<Function> hs = new LinkedHashSet<>();
|
final Set<Function> hs = new LinkedHashSet<>();
|
||||||
hs.addAll(results);
|
hs.addAll(results);
|
||||||
results.clear();
|
results.clear();
|
||||||
results.addAll(hs);
|
results.addAll(hs);
|
||||||
calc.f2 = results;
|
calc.f2 = results;
|
||||||
for (Function rf : calc.f2) {
|
for (final Function rf : calc.f2) {
|
||||||
rf.generateGraphics();
|
rf.generateGraphics();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (final Exception ex) {
|
||||||
if (Utils.debugOn) {
|
if (Utils.debugOn) {
|
||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
StringWriter sw = new StringWriter();
|
final StringWriter sw = new StringWriter();
|
||||||
PrintWriter pw = new PrintWriter(sw);
|
final PrintWriter pw = new PrintWriter(sw);
|
||||||
e.printStackTrace(pw);
|
e.printStackTrace(pw);
|
||||||
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
d.errorStackTrace = sw.toString().toUpperCase().replace("\t", " ").replace("\r", "").split("\n");
|
||||||
PIDisplay.error = e.id.toString();
|
DisplayManager.error = e.id.toString();
|
||||||
System.err.println(e.id);
|
System.err.println(e.id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void changeEquationScreen() {
|
private void changeEquationScreen() {
|
||||||
if (equazioneCorrente != null && equazioneCorrente.length() > 0) {
|
if (equazioneCorrente != null && equazioneCorrente.length() > 0) {
|
||||||
MathInputScreen cloned = clone();
|
final MathInputScreen cloned = clone();
|
||||||
cloned.caretPos = cloned.equazioneCorrente.length();
|
cloned.caretPos = cloned.equazioneCorrente.length();
|
||||||
cloned.nuovaEquazione = cloned.equazioneCorrente;
|
cloned.nuovaEquazione = cloned.equazioneCorrente;
|
||||||
cloned.scrollX = PIDisplay.renderer.glGetStringWidth(fontBig, cloned.equazioneCorrente);
|
cloned.scrollX = fontBig.getStringWidth(cloned.equazioneCorrente);
|
||||||
try {cloned.interpreta(true);} catch (Error e) {}
|
try {
|
||||||
PIDisplay.INSTANCE.replaceScreen(cloned);
|
cloned.interpreta(true);
|
||||||
this.initialized = false;
|
} catch (final Error e) {}
|
||||||
PIDisplay.INSTANCE.setScreen(this);
|
DisplayManager.INSTANCE.replaceScreen(cloned);
|
||||||
|
initialized = false;
|
||||||
|
DisplayManager.INSTANCE.setScreen(this);
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void typeChar(String chr) {
|
public void typeChar(String chr) {
|
||||||
int len = chr.length();
|
final int len = chr.length();
|
||||||
nuovaEquazione=nuovaEquazione.substring(0, caretPos)+chr+nuovaEquazione.substring(caretPos, nuovaEquazione.length());
|
nuovaEquazione = nuovaEquazione.substring(0, caretPos) + chr + nuovaEquazione.substring(caretPos, nuovaEquazione.length());
|
||||||
caretPos+=len;
|
caretPos += len;
|
||||||
scrollX = PIDisplay.renderer.glGetStringWidth(fontBig, nuovaEquazione.substring(0, caretPos)+"|||");
|
scrollX = fontBig.getStringWidth(nuovaEquazione.substring(0, caretPos) + "|||");
|
||||||
showCaret = true;
|
showCaret = true;
|
||||||
showCaretDelta = 0L;
|
showCaretDelta = 0L;
|
||||||
afterDoNextStep = false;
|
afterDoNextStep = false;
|
||||||
try {
|
try {
|
||||||
interpreta(true);
|
interpreta(true);
|
||||||
} catch (Error e) {
|
} catch (final Error e) {}
|
||||||
}
|
|
||||||
// f.clear(); //TODO: I removed this line to prevent input blanking when pressing EQUALS button and cloning this screen, but I must see why I created this part of code.
|
// f.clear(); //TODO: I removed this line to prevent input blanking when pressing EQUALS button and cloning this screen, but I must see why I created this part of code.
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -685,24 +683,24 @@ public class MathInputScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void showVariablesDialog(final Runnable runnable) {
|
public void showVariablesDialog(final Runnable runnable) {
|
||||||
Thread ct = new Thread(()->{
|
final Thread ct = new Thread(() -> {
|
||||||
ArrayList<Function> variablesInFunctions = getVariables(calc.f.toArray(new Function[calc.f.size()]));
|
final ArrayList<Function> variablesInFunctions = getVariables(calc.f.toArray(new Function[calc.f.size()]));
|
||||||
for (VariableValue f : calc.variablesValues) {
|
for (final VariableValue f : calc.variablesValues) {
|
||||||
if (variablesInFunctions.contains(f.v)) {
|
if (variablesInFunctions.contains(f.v)) {
|
||||||
variablesInFunctions.remove(f.v);
|
variablesInFunctions.remove(f.v);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
boolean cancelled = false;
|
boolean cancelled = false;
|
||||||
for (Function f : variablesInFunctions) {
|
for (final Function f : variablesInFunctions) {
|
||||||
ChooseVariableValueScreen cvs = new ChooseVariableValueScreen(this, new VariableValue((Variable) f, new Number(calc, 0)));
|
final ChooseVariableValueScreen cvs = new ChooseVariableValueScreen(this, new VariableValue((Variable) f, new Number(calc, 0)));
|
||||||
PIDisplay.INSTANCE.setScreen(cvs);
|
DisplayManager.INSTANCE.setScreen(cvs);
|
||||||
try {
|
try {
|
||||||
while (PIDisplay.screen == cvs) {
|
while (DisplayManager.screen == cvs) {
|
||||||
Utils.debug.println(Thread.currentThread().getName());
|
Utils.debug.println(Thread.currentThread().getName());
|
||||||
Thread.sleep(200);
|
Thread.sleep(200);
|
||||||
}
|
}
|
||||||
} catch (InterruptedException e) {}
|
} catch (final InterruptedException e) {}
|
||||||
if (cvs.resultNumberValue == null) {
|
if (cvs.resultNumberValue == null) {
|
||||||
cancelled = true;
|
cancelled = true;
|
||||||
break;
|
break;
|
||||||
@ -716,7 +714,7 @@ public class MathInputScreen extends Screen {
|
|||||||
calc.variablesValues.add(new VariableValue((Variable) f, (Number) cvs.resultNumberValue));
|
calc.variablesValues.add(new VariableValue((Variable) f, (Number) cvs.resultNumberValue));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!cancelled) {
|
if (!cancelled) {
|
||||||
if (runnable != null) {
|
if (runnable != null) {
|
||||||
runnable.run();
|
runnable.run();
|
||||||
}
|
}
|
||||||
@ -730,14 +728,14 @@ public class MathInputScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private ArrayList<Function> getVariables(Function[] fncs) {
|
private ArrayList<Function> getVariables(Function[] fncs) {
|
||||||
ArrayList<Function> res = new ArrayList<>();
|
final ArrayList<Function> res = new ArrayList<>();
|
||||||
for (Function f : fncs) {
|
for (final Function f : fncs) {
|
||||||
if (f instanceof FunctionTwoValues) {
|
if (f instanceof FunctionTwoValues) {
|
||||||
res.addAll(getVariables(new Function[]{((FunctionTwoValues)f).getVariable1(), ((FunctionTwoValues)f).getVariable2()}));
|
res.addAll(getVariables(new Function[] { ((FunctionTwoValues) f).getVariable1(), ((FunctionTwoValues) f).getVariable2() }));
|
||||||
} else if (f instanceof FunctionMultipleValues) {
|
} else if (f instanceof FunctionMultipleValues) {
|
||||||
res.addAll(getVariables(((FunctionMultipleValues)f).getVariables()));
|
res.addAll(getVariables(((FunctionMultipleValues) f).getVariables()));
|
||||||
} else if (f instanceof AnteriorFunction) {
|
} else if (f instanceof AnteriorFunction) {
|
||||||
res.addAll(getVariables(new Function[]{((AnteriorFunction)f).getVariable()}));
|
res.addAll(getVariables(new Function[] { ((AnteriorFunction) f).getVariable() }));
|
||||||
} else if (f instanceof Variable) {
|
} else if (f instanceof Variable) {
|
||||||
if (!res.contains(f)) {
|
if (!res.contains(f)) {
|
||||||
res.add(f);
|
res.add(f);
|
||||||
@ -749,8 +747,8 @@ public class MathInputScreen extends Screen {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public MathInputScreen clone() {
|
public MathInputScreen clone() {
|
||||||
MathInputScreen es = this;
|
final MathInputScreen es = this;
|
||||||
MathInputScreen es2 = new MathInputScreen();
|
final MathInputScreen es2 = new MathInputScreen();
|
||||||
es2.scrollX = es.scrollX;
|
es2.scrollX = es.scrollX;
|
||||||
es2.nuovaEquazione = es.nuovaEquazione;
|
es2.nuovaEquazione = es.nuovaEquazione;
|
||||||
es2.equazioneCorrente = es.equazioneCorrente;
|
es2.equazioneCorrente = es.equazioneCorrente;
|
||||||
|
@ -1,10 +1,10 @@
|
|||||||
package org.warp.picalculator.gui.screens;
|
package org.warp.picalculator.gui.screens;
|
||||||
|
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
|
|
||||||
public abstract class Screen {
|
public abstract class Screen {
|
||||||
public PIDisplay d;
|
public DisplayManager d;
|
||||||
public boolean created = false;
|
public boolean created = false;
|
||||||
public boolean initialized = false;
|
public boolean initialized = false;
|
||||||
public boolean canBeInHistory = false;
|
public boolean canBeInHistory = false;
|
||||||
|
@ -3,13 +3,13 @@ package org.warp.picalculator.gui.screens;
|
|||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Main;
|
import org.warp.picalculator.Main;
|
||||||
import org.warp.picalculator.device.Keyboard.Key;
|
import org.warp.picalculator.device.Keyboard.Key;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
public class SolveEquationScreen extends Screen {
|
public class SolveEquationScreen extends Screen {
|
||||||
|
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
private MathInputScreen es;
|
private final MathInputScreen es;
|
||||||
|
|
||||||
public SolveEquationScreen(MathInputScreen es) {
|
public SolveEquationScreen(MathInputScreen es) {
|
||||||
super();
|
super();
|
||||||
@ -19,20 +19,19 @@ public class SolveEquationScreen extends Screen {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void created() throws InterruptedException {
|
public void created() throws InterruptedException {}
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void init() throws InterruptedException {}
|
public void init() throws InterruptedException {}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void render() {
|
public void render() {
|
||||||
PIDisplay.renderer.glColor4i(0, 0, 0, 64);
|
DisplayManager.renderer.glColor4i(0, 0, 0, 64);
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2+1, Main.screenSize[1]/4, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2 + 1, Main.screenSize[1] / 4, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2, Main.screenSize[1]/4+1, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2, Main.screenSize[1] / 4 + 1, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2+1, Main.screenSize[1]/4+1, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2 + 1, Main.screenSize[1] / 4 + 1, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
PIDisplay.renderer.glColor3i(255, 0, 0);
|
DisplayManager.renderer.glColor3i(255, 0, 0);
|
||||||
PIDisplay.renderer.glDrawStringCenter(Main.screenSize[0]/2, Main.screenSize[1]/4, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
DisplayManager.renderer.glDrawStringCenter(Main.screenSize[0] / 2, Main.screenSize[1] / 4, "WORK IN PROGRESS. THIS SCREEN MUST HAVE A GUI TO SELECT THE VARIABLE TO SOLVE.");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -49,13 +48,13 @@ public class SolveEquationScreen extends Screen {
|
|||||||
public boolean keyPressed(Key k) {
|
public boolean keyPressed(Key k) {
|
||||||
switch (k) {
|
switch (k) {
|
||||||
case LETTER_X:
|
case LETTER_X:
|
||||||
PIDisplay.INSTANCE.goBack();
|
DisplayManager.INSTANCE.goBack();
|
||||||
try {
|
try {
|
||||||
es.calc.solveExpression('X');
|
es.calc.solveExpression('X');
|
||||||
} catch (Error e) {
|
} catch (final Error e) {
|
||||||
Screen scr = PIDisplay.INSTANCE.getScreen();
|
final Screen scr = DisplayManager.INSTANCE.getScreen();
|
||||||
if (scr instanceof MathInputScreen) {
|
if (scr instanceof MathInputScreen) {
|
||||||
MathInputScreen escr = (MathInputScreen) scr;
|
final MathInputScreen escr = (MathInputScreen) scr;
|
||||||
escr.errorLevel = 1;
|
escr.errorLevel = 1;
|
||||||
//escr.err2 = e; //TODO: What is this variable, and why it doesn't exists?
|
//escr.err2 = e; //TODO: What is this variable, and why it doesn't exists?
|
||||||
} else {
|
} else {
|
||||||
|
@ -1,7 +1,5 @@
|
|||||||
package org.warp.picalculator.math;
|
package org.warp.picalculator.math;
|
||||||
|
|
||||||
public enum AngleMode {
|
public enum AngleMode {
|
||||||
DEG,
|
DEG, RAD, GRA
|
||||||
RAD,
|
|
||||||
GRA
|
|
||||||
}
|
}
|
||||||
|
@ -34,9 +34,9 @@ public class Calculator {
|
|||||||
if (!string.startsWith("{")) {
|
if (!string.startsWith("{")) {
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
String[] parts = string.substring(1).split("\\{");
|
final String[] parts = string.substring(1).split("\\{");
|
||||||
EquationsSystem s = new EquationsSystem(this);
|
final EquationsSystem s = new EquationsSystem(this);
|
||||||
for (String part : parts) {
|
for (final String part : parts) {
|
||||||
s.addFunctionToEnd(parseEquationString(part));
|
s.addFunctionToEnd(parseEquationString(part));
|
||||||
}
|
}
|
||||||
return s;
|
return s;
|
||||||
@ -48,14 +48,14 @@ public class Calculator {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public Function parseEquationString(String string) throws Error {
|
public Function parseEquationString(String string) throws Error {
|
||||||
String[] parts = string.split("=");
|
final String[] parts = string.split("=");
|
||||||
if (parts.length == 1) {
|
if (parts.length == 1) {
|
||||||
Equation e = new Equation(this, null, null);
|
final Equation e = new Equation(this, null, null);
|
||||||
e.setVariable1(new Expression(this, parts[0]));
|
e.setVariable1(new Expression(this, parts[0]));
|
||||||
e.setVariable2(new Number(this, BigInteger.ZERO));
|
e.setVariable2(new Number(this, BigInteger.ZERO));
|
||||||
return e;
|
return e;
|
||||||
} else if (parts.length == 2) {
|
} else if (parts.length == 2) {
|
||||||
Equation e = new Equation(this, null, null);
|
final Equation e = new Equation(this, null, null);
|
||||||
e.setVariable1(new Expression(this, parts[0]));
|
e.setVariable1(new Expression(this, parts[0]));
|
||||||
e.setVariable2(new Expression(this, parts[1]));
|
e.setVariable2(new Expression(this, parts[1]));
|
||||||
return e;
|
return e;
|
||||||
@ -66,19 +66,19 @@ public class Calculator {
|
|||||||
|
|
||||||
public ArrayList<Function> solveExpression(ArrayList<Function> input) throws Error {
|
public ArrayList<Function> solveExpression(ArrayList<Function> input) throws Error {
|
||||||
ArrayList<Function> results = new ArrayList<>();
|
ArrayList<Function> results = new ArrayList<>();
|
||||||
ArrayList<Function> partialResults = new ArrayList<>();
|
final ArrayList<Function> partialResults = new ArrayList<>();
|
||||||
for (Function f : input) {
|
for (final Function f : input) {
|
||||||
if (f instanceof Equation) {
|
if (f instanceof Equation) {
|
||||||
throw new IllegalArgumentException("Not an expression!");
|
throw new IllegalArgumentException("Not an expression!");
|
||||||
} else {
|
} else {
|
||||||
results.add(f);
|
results.add(f);
|
||||||
while (Utils.allSolved(results) == false) {
|
while (Utils.allSolved(results) == false) {
|
||||||
for (Function itm : results) {
|
for (final Function itm : results) {
|
||||||
if (itm.isSolved() == false) {
|
if (itm.isSolved() == false) {
|
||||||
long t1 = System.currentTimeMillis();
|
final long t1 = System.currentTimeMillis();
|
||||||
List<Function> dt = itm.solveOneStep();
|
final List<Function> dt = itm.solveOneStep();
|
||||||
long t2 = System.currentTimeMillis();
|
final long t2 = System.currentTimeMillis();
|
||||||
if (t2-t1 >= 3000) {
|
if (t2 - t1 >= 3000) {
|
||||||
throw new Error(Errors.TIMEOUT);
|
throw new Error(Errors.TIMEOUT);
|
||||||
}
|
}
|
||||||
partialResults.addAll(dt);
|
partialResults.addAll(dt);
|
||||||
@ -108,19 +108,19 @@ public class Calculator {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void parseInputString(String eqn) throws Error {
|
public void parseInputString(String eqn) throws Error {
|
||||||
ArrayList<Function> fncs = new ArrayList<>();
|
final ArrayList<Function> fncs = new ArrayList<>();
|
||||||
if (eqn.length() > 0) {
|
if (eqn.length() > 0) {
|
||||||
try {
|
try {
|
||||||
fncs.add(parseString(eqn.replace("sqrt", "Ⓐ").replace("^", "Ⓑ")));
|
fncs.add(parseString(eqn.replace("sqrt", "Ⓐ").replace("^", "Ⓑ")));
|
||||||
} catch (Exception ex) {
|
} catch (final Exception ex) {
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
f = fncs;
|
f = fncs;
|
||||||
for (Function f : f) {
|
for (final Function f : f) {
|
||||||
try {
|
try {
|
||||||
f.generateGraphics();
|
f.generateGraphics();
|
||||||
} catch (NullPointerException ex) {
|
} catch (final NullPointerException ex) {
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -51,7 +51,7 @@ public class MathematicalSymbols {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static String[] variables() {
|
public static String[] variables() {
|
||||||
return new String[] { "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "ⓧ", "Ⓨ", "Z", PI};
|
return new String[] { "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "ⓧ", "Ⓨ", "Z", PI };
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String[] genericSyntax() {
|
public static String[] genericSyntax() {
|
||||||
@ -59,13 +59,6 @@ public class MathematicalSymbols {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static String getGraphicRepresentation(String string) {
|
public static String getGraphicRepresentation(String string) {
|
||||||
return string
|
return string.replace("Ⓑ", "^").replace("Ⓒ", "SIN").replace("Ⓓ", "COS").replace("Ⓔ", "TAN").replace("Ⓕ", "ASIN").replace("Ⓖ", "ACOS").replace("Ⓗ", "ATAN");
|
||||||
.replace("Ⓑ", "^")
|
|
||||||
.replace("Ⓒ", "SIN")
|
|
||||||
.replace("Ⓓ", "COS")
|
|
||||||
.replace("Ⓔ", "TAN")
|
|
||||||
.replace("Ⓕ", "ASIN")
|
|
||||||
.replace("Ⓖ", "ACOS")
|
|
||||||
.replace("Ⓗ", "ATAN");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4,7 +4,7 @@ import java.util.ArrayList;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
@ -12,7 +12,7 @@ import com.rits.cloning.Cloner;
|
|||||||
|
|
||||||
public abstract class AnteriorFunction implements Function {
|
public abstract class AnteriorFunction implements Function {
|
||||||
public AnteriorFunction(Function value) {
|
public AnteriorFunction(Function value) {
|
||||||
this.root = value.getRoot();
|
root = value.getRoot();
|
||||||
variable = value;
|
variable = value;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -49,20 +49,20 @@ public abstract class AnteriorFunction implements Function {
|
|||||||
@Override
|
@Override
|
||||||
public final ArrayList<Function> solveOneStep() throws Error {
|
public final ArrayList<Function> solveOneStep() throws Error {
|
||||||
final boolean solved = variable.isSolved();
|
final boolean solved = variable.isSolved();
|
||||||
ArrayList<Function> result = solved?solve():null;
|
ArrayList<Function> result = solved ? solve() : null;
|
||||||
|
|
||||||
if (result == null || result.isEmpty()) {
|
if (result == null || result.isEmpty()) {
|
||||||
result = new ArrayList<>();
|
result = new ArrayList<>();
|
||||||
|
|
||||||
ArrayList<Function> l1 = new ArrayList<>();
|
final ArrayList<Function> l1 = new ArrayList<>();
|
||||||
if (variable.isSolved()) {
|
if (variable.isSolved()) {
|
||||||
l1.add(variable);
|
l1.add(variable);
|
||||||
} else {
|
} else {
|
||||||
l1.addAll(variable.solveOneStep());
|
l1.addAll(variable.solveOneStep());
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Function f : l1) {
|
for (final Function f : l1) {
|
||||||
result.add(NewInstance(this.root, f));
|
result.add(NewInstance(root, f));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -83,20 +83,20 @@ public abstract class AnteriorFunction implements Function {
|
|||||||
variable.setSmall(small);
|
variable.setSmall(small);
|
||||||
variable.generateGraphics();
|
variable.generateGraphics();
|
||||||
|
|
||||||
width = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol()) + 1 + getVariable().getWidth();
|
width = DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), getSymbol()) + 1 + getVariable().getWidth();
|
||||||
height = variable.getHeight();
|
height = variable.getHeight();
|
||||||
line = variable.getLine();
|
line = variable.getLine();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
float h1 = getVariable().getHeight();
|
final float h1 = getVariable().getHeight();
|
||||||
int wsegno = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
final int wsegno = DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
||||||
float hsegno = Utils.getFontHeight(small);
|
final float hsegno = Utils.getFontHeight(small);
|
||||||
float maxh = getHeight();
|
final float maxh = getHeight();
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
DisplayManager.renderer.glSetFont(Utils.getFont(small));
|
||||||
|
|
||||||
PIDisplay.renderer.glDrawStringLeft(x, (int) Math.floor(y + (maxh - hsegno) / 2), getSymbol());
|
DisplayManager.renderer.glDrawStringLeft(x, (int) Math.floor(y + (maxh - hsegno) / 2), getSymbol());
|
||||||
getVariable().draw(x + wsegno + 1, (int) Math.floor(y + (maxh - h1) / 2));
|
getVariable().draw(x + wsegno + 1, (int) Math.floor(y + (maxh - h1) / 2));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -123,7 +123,7 @@ public abstract class AnteriorFunction implements Function {
|
|||||||
if (variable != null) {
|
if (variable != null) {
|
||||||
val1 = variable.toString();
|
val1 = variable.toString();
|
||||||
}
|
}
|
||||||
return getSymbol()+val1;
|
return getSymbol() + val1;
|
||||||
// } catch (Error e) {
|
// } catch (Error e) {
|
||||||
// return e.id.toString();
|
// return e.id.toString();
|
||||||
// }
|
// }
|
||||||
@ -131,7 +131,7 @@ public abstract class AnteriorFunction implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public AnteriorFunction clone() {
|
public AnteriorFunction clone() {
|
||||||
Cloner cloner = new Cloner();
|
final Cloner cloner = new Cloner();
|
||||||
return cloner.deepClone(this);
|
return cloner.deepClone(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -142,7 +142,7 @@ public abstract class AnteriorFunction implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int hashCode() {
|
public int hashCode() {
|
||||||
return variable.hashCode()+883*getSymbol().hashCode();
|
return variable.hashCode() + 883 * getSymbol().hashCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -4,7 +4,7 @@ import java.util.ArrayList;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
@ -29,13 +29,20 @@ public class Division extends FunctionTwoValues {
|
|||||||
return MathematicalSymbols.DIVISION;
|
return MathematicalSymbols.DIVISION;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected boolean isSolvable() {
|
protected boolean isSolvable() {
|
||||||
if (FractionsRule1.compare(this)) return true;
|
if (FractionsRule1.compare(this)) {
|
||||||
if (FractionsRule2.compare(this)) return true;
|
return true;
|
||||||
if (FractionsRule3.compare(this)) return true;
|
}
|
||||||
if (UndefinedRule2.compare(this)) return true;
|
if (FractionsRule2.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (FractionsRule3.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (UndefinedRule2.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
if (variable1 instanceof Number && variable2 instanceof Number && root.exactMode == false) {
|
if (variable1 instanceof Number && variable2 instanceof Number && root.exactMode == false) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -54,13 +61,13 @@ public class Division extends FunctionTwoValues {
|
|||||||
} else if (UndefinedRule2.compare(this)) {
|
} else if (UndefinedRule2.compare(this)) {
|
||||||
result = UndefinedRule2.execute(this);
|
result = UndefinedRule2.execute(this);
|
||||||
} else if (variable1 instanceof Number && variable2 instanceof Number && root.exactMode == false) {
|
} else if (variable1 instanceof Number && variable2 instanceof Number && root.exactMode == false) {
|
||||||
result.add(((Number)variable1).divide((Number)variable2));
|
result.add(((Number) variable1).divide((Number) variable2));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean hasMinus() {
|
public boolean hasMinus() {
|
||||||
String numerator = variable1.toString();
|
final String numerator = variable1.toString();
|
||||||
if (numerator.startsWith("-")) {
|
if (numerator.startsWith("-")) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -68,7 +75,7 @@ public class Division extends FunctionTwoValues {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void draw(int x, int y, boolean small, boolean drawMinus) {
|
public void draw(int x, int y, boolean small, boolean drawMinus) {
|
||||||
boolean beforedrawminus = this.drawMinus;
|
final boolean beforedrawminus = this.drawMinus;
|
||||||
this.drawMinus = drawMinus;
|
this.drawMinus = drawMinus;
|
||||||
draw(x, y);
|
draw(x, y);
|
||||||
this.drawMinus = beforedrawminus;
|
this.drawMinus = beforedrawminus;
|
||||||
@ -93,8 +100,8 @@ public class Division extends FunctionTwoValues {
|
|||||||
// glFillRect(x,y,width,height);
|
// glFillRect(x,y,width,height);
|
||||||
// glColor3f(0, 0, 0);
|
// glColor3f(0, 0, 0);
|
||||||
|
|
||||||
Object var1 = variable1;
|
final Object var1 = variable1;
|
||||||
Object var2 = variable2;
|
final Object var2 = variable2;
|
||||||
boolean minus = false;
|
boolean minus = false;
|
||||||
int minusw = 0;
|
int minusw = 0;
|
||||||
int minush = 0;
|
int minush = 0;
|
||||||
@ -105,15 +112,15 @@ public class Division extends FunctionTwoValues {
|
|||||||
}
|
}
|
||||||
int w1 = 0;
|
int w1 = 0;
|
||||||
int h1 = 0;
|
int h1 = 0;
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
Utils.getFont(small).use(DisplayManager.display);
|
||||||
if (minus) {
|
if (minus) {
|
||||||
w1 = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), numerator);
|
w1 = Utils.getFont(small).getStringWidth(numerator);
|
||||||
h1 = Utils.getFont(small).charH;
|
h1 = Utils.getFont(small).getCharacterHeight();
|
||||||
} else {
|
} else {
|
||||||
w1 = ((Function) var1).getWidth();
|
w1 = ((Function) var1).getWidth();
|
||||||
h1 = ((Function) var1).getHeight();
|
h1 = ((Function) var1).getHeight();
|
||||||
}
|
}
|
||||||
int w2 = ((Function) var2).getWidth();
|
final int w2 = ((Function) var2).getWidth();
|
||||||
int maxw;
|
int maxw;
|
||||||
if (w1 > w2) {
|
if (w1 > w2) {
|
||||||
maxw = 1 + w1;
|
maxw = 1 + w1;
|
||||||
@ -121,15 +128,15 @@ public class Division extends FunctionTwoValues {
|
|||||||
maxw = 1 + w2;
|
maxw = 1 + w2;
|
||||||
}
|
}
|
||||||
if (minus && drawMinus) {
|
if (minus && drawMinus) {
|
||||||
minusw = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), "-") + 1;
|
minusw = Utils.getFont(small).getCharacterWidth() /* Width of minus */ + 1;
|
||||||
minush = Utils.getFont(small).charH;
|
minush = Utils.getFont(small).getCharacterHeight();
|
||||||
PIDisplay.renderer.glDrawStringLeft(x+1, y + h1 + 1 + 1 - (minush / 2), "-");
|
DisplayManager.renderer.glDrawStringLeft(x + 1, y + h1 + 1 + 1 - (minush / 2), "-");
|
||||||
PIDisplay.renderer.glDrawStringLeft((int) (x+1 + minusw + 1 + (maxw - w1) / 2d), y, numerator);
|
DisplayManager.renderer.glDrawStringLeft((int) (x + 1 + minusw + 1 + (maxw - w1) / 2d), y, numerator);
|
||||||
} else {
|
} else {
|
||||||
((Function) var1).draw((int) (x+1 + minusw + (maxw - w1) / 2d), y);
|
((Function) var1).draw((int) (x + 1 + minusw + (maxw - w1) / 2d), y);
|
||||||
}
|
}
|
||||||
((Function) var2).draw((int) (x+1 + minusw + (maxw - w2) / 2d), y + h1 + 1 + 1 + 1);
|
((Function) var2).draw((int) (x + 1 + minusw + (maxw - w2) / 2d), y + h1 + 1 + 1 + 1);
|
||||||
PIDisplay.renderer.glFillRect(x+1+ minusw, y + h1 + 1, maxw, 1);
|
DisplayManager.renderer.glFillColor(x + 1 + minusw, y + h1 + 1, maxw, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -152,7 +159,7 @@ public class Division extends FunctionTwoValues {
|
|||||||
} else {
|
} else {
|
||||||
h1 = variable1.getHeight();
|
h1 = variable1.getHeight();
|
||||||
}
|
}
|
||||||
int h2 = variable2.getHeight();
|
final int h2 = variable2.getHeight();
|
||||||
return h1 + 3 + h2;
|
return h1 + 3 + h2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -176,19 +183,19 @@ public class Division extends FunctionTwoValues {
|
|||||||
}
|
}
|
||||||
int w1 = 0;
|
int w1 = 0;
|
||||||
if (minus) {
|
if (minus) {
|
||||||
w1 = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), numerator);
|
w1 = Utils.getFont(small).getStringWidth(numerator);
|
||||||
} else {
|
} else {
|
||||||
w1 = variable1.getWidth();
|
w1 = variable1.getWidth();
|
||||||
}
|
}
|
||||||
int w2 = variable2.getWidth();
|
final int w2 = variable2.getWidth();
|
||||||
int maxw = 0;
|
int maxw = 0;
|
||||||
if (w1 > w2) {
|
if (w1 > w2) {
|
||||||
maxw = w1+1;
|
maxw = w1 + 1;
|
||||||
} else {
|
} else {
|
||||||
maxw = w2+1;
|
maxw = w2 + 1;
|
||||||
}
|
}
|
||||||
if (minus && drawMinus) {
|
if (minus && drawMinus) {
|
||||||
return 1 + PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), "-") + 1 + maxw;
|
return 1 + Utils.getFont(small).getCharacterWidth() /* Width of minus */ + 1 + maxw;
|
||||||
} else {
|
} else {
|
||||||
return 1 + maxw;
|
return 1 + maxw;
|
||||||
}
|
}
|
||||||
@ -197,7 +204,7 @@ public class Division extends FunctionTwoValues {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Division) {
|
if (o instanceof Division) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
@ -4,7 +4,7 @@ import java.util.List;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
@ -39,12 +39,12 @@ public class EmptyNumber implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
PIDisplay.renderer.glDrawStringLeft(x, y, "␀");
|
DisplayManager.renderer.glDrawStringLeft(x, y, "␀");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getWidth() {
|
public int getWidth() {
|
||||||
return PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), "␀");
|
return DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), "␀");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -54,7 +54,7 @@ public class EmptyNumber implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getLine() {
|
public int getLine() {
|
||||||
return Utils.getFont(small).charH/2;
|
return Utils.getFont(small).charH / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -12,7 +12,7 @@ import java.util.regex.Pattern;
|
|||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Errors;
|
import org.warp.picalculator.Errors;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
import org.warp.picalculator.math.functions.trigonometry.ArcCosine;
|
import org.warp.picalculator.math.functions.trigonometry.ArcCosine;
|
||||||
@ -48,7 +48,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
try {
|
try {
|
||||||
new Number(root, string);
|
new Number(root, string);
|
||||||
isNumber = true;
|
isNumber = true;
|
||||||
} catch (NumberFormatException ex) {
|
} catch (final NumberFormatException ex) {
|
||||||
isNumber = false;
|
isNumber = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -57,10 +57,10 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
|
|
||||||
isNumber = false; //TODO: rimuovere isNumber, alcune semplificazione come la divisione per zero altrimenti verrebbero saltate.
|
isNumber = false; //TODO: rimuovere isNumber, alcune semplificazione come la divisione per zero altrimenti verrebbero saltate.
|
||||||
|
|
||||||
if (isNumber){
|
if (isNumber) {
|
||||||
// If the expression is already a number:
|
// If the expression is already a number:
|
||||||
// Se l'espressione è già un numero:
|
// Se l'espressione è già un numero:
|
||||||
Number t = new Number(root, string);
|
final Number t = new Number(root, string);
|
||||||
setVariables(new Function[] { t });
|
setVariables(new Function[] { t });
|
||||||
Utils.debug.println(debugSpaces + "•Result:" + t.toString());
|
Utils.debug.println(debugSpaces + "•Result:" + t.toString());
|
||||||
} else {
|
} else {
|
||||||
@ -75,7 +75,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
// Controlla se ci sono più di un uguale (=)
|
// Controlla se ci sono più di un uguale (=)
|
||||||
int equationsFound = 0;
|
int equationsFound = 0;
|
||||||
int systemsFound = 0;
|
int systemsFound = 0;
|
||||||
for (char c : processExpression.toCharArray()) {
|
for (final char c : processExpression.toCharArray()) {
|
||||||
if (("" + c).equals(MathematicalSymbols.EQUATION)) {
|
if (("" + c).equals(MathematicalSymbols.EQUATION)) {
|
||||||
equationsFound += 1;
|
equationsFound += 1;
|
||||||
}
|
}
|
||||||
@ -98,7 +98,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
boolean symbolsChanged = false;
|
boolean symbolsChanged = false;
|
||||||
while (matcher.find()) {
|
while (matcher.find()) {
|
||||||
symbolsChanged = true;
|
symbolsChanged = true;
|
||||||
String correzione = "+";
|
final String correzione = "+";
|
||||||
processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
||||||
matcher = pattern.matcher(processExpression);
|
matcher = pattern.matcher(processExpression);
|
||||||
}
|
}
|
||||||
@ -109,7 +109,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
matcher = pattern.matcher(processExpression);
|
matcher = pattern.matcher(processExpression);
|
||||||
while (matcher.find()) {
|
while (matcher.find()) {
|
||||||
symbolsChanged = true;
|
symbolsChanged = true;
|
||||||
String correzione = "-";
|
final String correzione = "-";
|
||||||
processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
||||||
matcher = pattern.matcher(processExpression);
|
matcher = pattern.matcher(processExpression);
|
||||||
}
|
}
|
||||||
@ -138,7 +138,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
symbolsChanged = false;
|
symbolsChanged = false;
|
||||||
while (matcher.find()) {
|
while (matcher.find()) {
|
||||||
symbolsChanged = true;
|
symbolsChanged = true;
|
||||||
String correzione = matcher.group(0).replaceFirst(Matcher.quoteReplacement("+"), "");
|
final String correzione = matcher.group(0).replaceFirst(Matcher.quoteReplacement("+"), "");
|
||||||
processExpression = processExpression.substring(0, matcher.start(0) + 1) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
processExpression = processExpression.substring(0, matcher.start(0) + 1) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
||||||
matcher = pattern.matcher(processExpression);
|
matcher = pattern.matcher(processExpression);
|
||||||
}
|
}
|
||||||
@ -151,7 +151,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
matcher = pattern.matcher(processExpression);
|
matcher = pattern.matcher(processExpression);
|
||||||
while (matcher.find()) {
|
while (matcher.find()) {
|
||||||
symbolsChanged = true;
|
symbolsChanged = true;
|
||||||
String correzione = MathematicalSymbols.MINUS;
|
final String correzione = MathematicalSymbols.MINUS;
|
||||||
processExpression = processExpression.substring(0, matcher.start(0) + 1) + correzione + processExpression.substring(matcher.start(0) + 2, processExpression.length());
|
processExpression = processExpression.substring(0, matcher.start(0) + 1) + correzione + processExpression.substring(matcher.start(0) + 2, processExpression.length());
|
||||||
matcher = pattern.matcher(processExpression);
|
matcher = pattern.matcher(processExpression);
|
||||||
}
|
}
|
||||||
@ -186,7 +186,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
symbolsChanged = true;
|
symbolsChanged = true;
|
||||||
// sistema i segni * impliciti prima e dopo l'espressione.
|
// sistema i segni * impliciti prima e dopo l'espressione.
|
||||||
String beforeexp = processExpression.substring(0, matcher.start(0));
|
String beforeexp = processExpression.substring(0, matcher.start(0));
|
||||||
String newexp = matcher.group(0).substring(1, matcher.group(0).length() - 1);
|
final String newexp = matcher.group(0).substring(1, matcher.group(0).length() - 1);
|
||||||
String afterexp = processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
String afterexp = processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
|
||||||
if (Pattern.compile("[^\\-" + Utils.ArrayToRegex(Utils.add(concat(MathematicalSymbols.functions(), concat(MathematicalSymbols.signums(true), MathematicalSymbols.genericSyntax())), "(")) + "]$").matcher(beforeexp).find()) {
|
if (Pattern.compile("[^\\-" + Utils.ArrayToRegex(Utils.add(concat(MathematicalSymbols.functions(), concat(MathematicalSymbols.signums(true), MathematicalSymbols.genericSyntax())), "(")) + "]$").matcher(beforeexp).find()) {
|
||||||
// Se la stringa precedente finisce con un numero
|
// Se la stringa precedente finisce con un numero
|
||||||
@ -211,13 +211,13 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
debugSpaces += " ";
|
debugSpaces += " ";
|
||||||
|
|
||||||
// Convert the expression to a list of objects
|
// Convert the expression to a list of objects
|
||||||
Expression imputRawParenthesis = new Expression(root);
|
final Expression imputRawParenthesis = new Expression(root);
|
||||||
imputRawParenthesis.setVariables(new Function[] {});
|
imputRawParenthesis.setVariables(new Function[] {});
|
||||||
String tmp = "";
|
String tmp = "";
|
||||||
final String[] functions = concat(concat(concat(concat(MathematicalSymbols.functions(), MathematicalSymbols.parentheses()), MathematicalSymbols.signums(true)), MathematicalSymbols.variables()), MathematicalSymbols.genericSyntax());
|
final String[] functions = concat(concat(concat(concat(MathematicalSymbols.functions(), MathematicalSymbols.parentheses()), MathematicalSymbols.signums(true)), MathematicalSymbols.variables()), MathematicalSymbols.genericSyntax());
|
||||||
for (int i = 0; i < processExpression.length(); i++) {
|
for (int i = 0; i < processExpression.length(); i++) {
|
||||||
// Per ogni carattere cerca se è un numero o una funzione:
|
// Per ogni carattere cerca se è un numero o una funzione:
|
||||||
String charI = processExpression.charAt(i) + "";
|
final String charI = processExpression.charAt(i) + "";
|
||||||
if (Utils.isInArray(charI, functions)) {
|
if (Utils.isInArray(charI, functions)) {
|
||||||
|
|
||||||
// Finds the type of function fron the following list
|
// Finds the type of function fron the following list
|
||||||
@ -326,7 +326,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
Utils.debug.println(debugSpaces + "•Added multiplication to expression:" + new Multiplication(root, null, null).getSymbol());
|
Utils.debug.println(debugSpaces + "•Added multiplication to expression:" + new Multiplication(root, null, null).getSymbol());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
Function precedentFunction = imputRawParenthesis.getVariable(imputRawParenthesis.getVariablesLength() - 1);
|
final Function precedentFunction = imputRawParenthesis.getVariable(imputRawParenthesis.getVariablesLength() - 1);
|
||||||
if (tmp.length() > 0) {
|
if (tmp.length() > 0) {
|
||||||
if (precedentFunction instanceof Number || precedentFunction instanceof Variable) {
|
if (precedentFunction instanceof Number || precedentFunction instanceof Variable) {
|
||||||
imputRawParenthesis.addFunctionToEnd(new Multiplication(root, null, null));
|
imputRawParenthesis.addFunctionToEnd(new Multiplication(root, null, null));
|
||||||
@ -366,7 +366,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
// Se il carattere è un numero intero, un segno
|
// Se il carattere è un numero intero, un segno
|
||||||
// negativo, o un punto
|
// negativo, o un punto
|
||||||
tmp += charI;
|
tmp += charI;
|
||||||
} catch (Exception exc) {
|
} catch (final Exception exc) {
|
||||||
throw new java.lang.RuntimeException("Il carattere " + tmp + charI + " non è nè un numero nè un espressione presente nella lista completa!\nAggiungerlo ad essa o rimuovere il carattere dall'espressione!");
|
throw new java.lang.RuntimeException("Il carattere " + tmp + charI + " non è nè un numero nè un espressione presente nella lista completa!\nAggiungerlo ad essa o rimuovere il carattere dall'espressione!");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -375,7 +375,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
Utils.debug.println(debugSpaces + "•Added variable to expression:" + tmp);
|
Utils.debug.println(debugSpaces + "•Added variable to expression:" + tmp);
|
||||||
try {
|
try {
|
||||||
imputRawParenthesis.addFunctionToEnd(new Number(root, tmp));
|
imputRawParenthesis.addFunctionToEnd(new Number(root, tmp));
|
||||||
} catch (NumberFormatException ex) {
|
} catch (final NumberFormatException ex) {
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
tmp = "";
|
tmp = "";
|
||||||
@ -392,9 +392,9 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
Utils.debug.println(debugSpaces + "•Removing useless parentheses");
|
Utils.debug.println(debugSpaces + "•Removing useless parentheses");
|
||||||
for (int i = 0; i < imputRawParenthesis.functions.length; i++) {
|
for (int i = 0; i < imputRawParenthesis.functions.length; i++) {
|
||||||
if (imputRawParenthesis.functions[i] instanceof Expression) {
|
if (imputRawParenthesis.functions[i] instanceof Expression) {
|
||||||
Expression par = (Expression) imputRawParenthesis.functions[i];
|
final Expression par = (Expression) imputRawParenthesis.functions[i];
|
||||||
if (par.functions.length == 1) {
|
if (par.functions.length == 1) {
|
||||||
Function subFunz = par.functions[0];
|
final Function subFunz = par.functions[0];
|
||||||
if (subFunz instanceof Expression || subFunz instanceof Number || subFunz instanceof Variable) {
|
if (subFunz instanceof Expression || subFunz instanceof Number || subFunz instanceof Variable) {
|
||||||
imputRawParenthesis.functions[i] = subFunz;
|
imputRawParenthesis.functions[i] = subFunz;
|
||||||
Utils.debug.println(debugSpaces + " •Useless parentheses removed");
|
Utils.debug.println(debugSpaces + " •Useless parentheses removed");
|
||||||
@ -406,17 +406,17 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
// Inizia l'affinazione dell'espressione
|
// Inizia l'affinazione dell'espressione
|
||||||
Utils.debug.println(debugSpaces + "•Pushing classes...");
|
Utils.debug.println(debugSpaces + "•Pushing classes...");
|
||||||
|
|
||||||
Function[] oldFunctionsArray = imputRawParenthesis.getVariables();
|
final Function[] oldFunctionsArray = imputRawParenthesis.getVariables();
|
||||||
ArrayList<Function> oldFunctionsList = new ArrayList<>();
|
final ArrayList<Function> oldFunctionsList = new ArrayList<>();
|
||||||
for (int i = 0; i < oldFunctionsArray.length; i++) {
|
for (int i = 0; i < oldFunctionsArray.length; i++) {
|
||||||
Function funzione = oldFunctionsArray[i];
|
Function funzione = oldFunctionsArray[i];
|
||||||
if (funzione != null) {
|
if (funzione != null) {
|
||||||
//Affinazione
|
//Affinazione
|
||||||
if (funzione instanceof Root) {
|
if (funzione instanceof Root) {
|
||||||
if ((i - 1) >= 0 && oldFunctionsArray[i-1] instanceof Number && ((Number)oldFunctionsArray[i-1]).getTerm().compareTo(new BigDecimal(2)) == 0) {
|
if ((i - 1) >= 0 && oldFunctionsArray[i - 1] instanceof Number && ((Number) oldFunctionsArray[i - 1]).getTerm().compareTo(new BigDecimal(2)) == 0) {
|
||||||
oldFunctionsArray[i] = null;
|
oldFunctionsArray[i] = null;
|
||||||
oldFunctionsArray[i-1] = null;
|
oldFunctionsArray[i - 1] = null;
|
||||||
oldFunctionsList.remove(oldFunctionsList.size()-1);
|
oldFunctionsList.remove(oldFunctionsList.size() - 1);
|
||||||
i -= 1;
|
i -= 1;
|
||||||
funzione = new RootSquare(root, null);
|
funzione = new RootSquare(root, null);
|
||||||
}
|
}
|
||||||
@ -452,64 +452,12 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
oldFunctionsList.set(0, new Multiplication(root, oldFunctionsList.get(0), oldFunctionsList.remove(1)));
|
oldFunctionsList.set(0, new Multiplication(root, oldFunctionsList.get(0), oldFunctionsList.remove(1)));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Utils.debug.println(debugSpaces + " •Phase: "+step);
|
Utils.debug.println(debugSpaces + " •Phase: " + step);
|
||||||
while (i < oldFunctionsList.size() && change == false && oldFunctionsList.size() > 1) {
|
while (i < oldFunctionsList.size() && change == false && oldFunctionsList.size() > 1) {
|
||||||
Function funzioneTMP = oldFunctionsList.get(i);
|
final Function funzioneTMP = oldFunctionsList.get(i);
|
||||||
if (funzioneTMP instanceof FunctionTwoValues) {
|
if (funzioneTMP instanceof FunctionTwoValues) {
|
||||||
if (step != "SN Functions") {
|
if (step != "SN Functions") {
|
||||||
if (
|
if ((step == "sums" && (funzioneTMP instanceof Sum || funzioneTMP instanceof SumSubtraction || funzioneTMP instanceof Subtraction) == true && ((funzioneTMP instanceof AnteriorFunction && ((AnteriorFunction) funzioneTMP).variable == null) || (funzioneTMP instanceof FunctionTwoValues && ((FunctionTwoValues) funzioneTMP).variable1 == null && ((FunctionTwoValues) funzioneTMP).variable2 == null) || (!(funzioneTMP instanceof AnteriorFunction) && !(funzioneTMP instanceof FunctionTwoValues)))) || (step.equals("multiplications") && ((funzioneTMP instanceof Multiplication) || (funzioneTMP instanceof Division)) && ((FunctionTwoValues) funzioneTMP).variable1 == null && ((FunctionTwoValues) funzioneTMP).variable2 == null) || (step == "NSN Functions" && (funzioneTMP instanceof Sum) == false && (funzioneTMP instanceof SumSubtraction) == false && (funzioneTMP instanceof Subtraction) == false && (funzioneTMP instanceof Multiplication) == false && (funzioneTMP instanceof Division) == false && ((funzioneTMP instanceof AnteriorFunction && ((AnteriorFunction) funzioneTMP).variable == null) || (funzioneTMP instanceof FunctionTwoValues && ((FunctionTwoValues) funzioneTMP).variable1 == null && ((FunctionTwoValues) funzioneTMP).variable2 == null) || (!(funzioneTMP instanceof AnteriorFunction) && !(funzioneTMP instanceof FunctionTwoValues))))) {
|
||||||
(step == "sums" && (funzioneTMP instanceof Sum || funzioneTMP instanceof SumSubtraction || funzioneTMP instanceof Subtraction) == true && ((funzioneTMP instanceof AnteriorFunction && ((AnteriorFunction) funzioneTMP).variable == null) || (funzioneTMP instanceof FunctionTwoValues && ((FunctionTwoValues) funzioneTMP).variable1 == null && ((FunctionTwoValues) funzioneTMP).variable2 == null) || (!(funzioneTMP instanceof AnteriorFunction) && !(funzioneTMP instanceof FunctionTwoValues))))
|
|
||||||
||
|
|
||||||
(
|
|
||||||
step.equals("multiplications")
|
|
||||||
&&
|
|
||||||
(
|
|
||||||
(funzioneTMP instanceof Multiplication)
|
|
||||||
||
|
|
||||||
(funzioneTMP instanceof Division)
|
|
||||||
)
|
|
||||||
&&
|
|
||||||
((FunctionTwoValues) funzioneTMP).variable1 == null
|
|
||||||
&&
|
|
||||||
((FunctionTwoValues) funzioneTMP).variable2 == null
|
|
||||||
)
|
|
||||||
||
|
|
||||||
(
|
|
||||||
step == "NSN Functions"
|
|
||||||
&&
|
|
||||||
(funzioneTMP instanceof Sum) == false
|
|
||||||
&&
|
|
||||||
(funzioneTMP instanceof SumSubtraction) == false
|
|
||||||
&&
|
|
||||||
(funzioneTMP instanceof Subtraction) == false
|
|
||||||
&&
|
|
||||||
(funzioneTMP instanceof Multiplication) == false
|
|
||||||
&&
|
|
||||||
(funzioneTMP instanceof Division) == false
|
|
||||||
&&
|
|
||||||
(
|
|
||||||
(
|
|
||||||
funzioneTMP instanceof AnteriorFunction
|
|
||||||
&&
|
|
||||||
((AnteriorFunction) funzioneTMP).variable == null
|
|
||||||
)
|
|
||||||
||
|
|
||||||
(
|
|
||||||
funzioneTMP instanceof FunctionTwoValues
|
|
||||||
&&
|
|
||||||
((FunctionTwoValues) funzioneTMP).variable1 == null
|
|
||||||
&&
|
|
||||||
((FunctionTwoValues) funzioneTMP).variable2 == null
|
|
||||||
)
|
|
||||||
||
|
|
||||||
(
|
|
||||||
!(funzioneTMP instanceof AnteriorFunction)
|
|
||||||
&&
|
|
||||||
!(funzioneTMP instanceof FunctionTwoValues)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
) {
|
|
||||||
change = true;
|
change = true;
|
||||||
|
|
||||||
if (i + 1 < oldFunctionsList.size() && i - 1 >= 0) {
|
if (i + 1 < oldFunctionsList.size() && i - 1 >= 0) {
|
||||||
@ -526,13 +474,13 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
Utils.debug.println(debugSpaces + " •Set variable to expression:" + funzioneTMP.getSymbol());
|
Utils.debug.println(debugSpaces + " •Set variable to expression:" + funzioneTMP.getSymbol());
|
||||||
try {
|
try {
|
||||||
Utils.debug.println(debugSpaces + " " + "var1=" + ((FunctionTwoValues) funzioneTMP).getVariable1().toString());
|
Utils.debug.println(debugSpaces + " " + "var1=" + ((FunctionTwoValues) funzioneTMP).getVariable1().toString());
|
||||||
} catch (NullPointerException ex2) {}
|
} catch (final NullPointerException ex2) {}
|
||||||
try {
|
try {
|
||||||
Utils.debug.println(debugSpaces + " " + "var2=" + ((FunctionTwoValues) funzioneTMP).getVariable2().toString());
|
Utils.debug.println(debugSpaces + " " + "var2=" + ((FunctionTwoValues) funzioneTMP).getVariable2().toString());
|
||||||
} catch (NullPointerException ex2) {}
|
} catch (final NullPointerException ex2) {}
|
||||||
try {
|
try {
|
||||||
Utils.debug.println(debugSpaces + " " + "(result)=" + ((FunctionTwoValues) funzioneTMP).toString());
|
Utils.debug.println(debugSpaces + " " + "(result)=" + ((FunctionTwoValues) funzioneTMP).toString());
|
||||||
} catch (NullPointerException ex2) {}
|
} catch (final NullPointerException ex2) {}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
@ -542,8 +490,8 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
} else if (funzioneTMP instanceof AnteriorFunction) {
|
} else if (funzioneTMP instanceof AnteriorFunction) {
|
||||||
if ((step == "SN Functions" && ((AnteriorFunction) funzioneTMP).variable == null)) {
|
if ((step == "SN Functions" && ((AnteriorFunction) funzioneTMP).variable == null)) {
|
||||||
if (i + 1 < oldFunctionsList.size()) {
|
if (i + 1 < oldFunctionsList.size()) {
|
||||||
Function nextFunc = oldFunctionsList.get(i + 1);
|
final Function nextFunc = oldFunctionsList.get(i + 1);
|
||||||
if (nextFunc instanceof AnteriorFunction && ((AnteriorFunction)nextFunc).variable == null) {
|
if (nextFunc instanceof AnteriorFunction && ((AnteriorFunction) nextFunc).variable == null) {
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
change = true;
|
change = true;
|
||||||
@ -556,7 +504,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
oldFunctionsList.remove(i + 1);
|
oldFunctionsList.remove(i + 1);
|
||||||
|
|
||||||
Utils.debug.println(debugSpaces + " •Set variable to expression:" + funzioneTMP.getSymbol());
|
Utils.debug.println(debugSpaces + " •Set variable to expression:" + funzioneTMP.getSymbol());
|
||||||
Function var = ((AnteriorFunction) funzioneTMP).getVariable();
|
final Function var = ((AnteriorFunction) funzioneTMP).getVariable();
|
||||||
if (var == null) {
|
if (var == null) {
|
||||||
Utils.debug.println(debugSpaces + " " + "var=null");
|
Utils.debug.println(debugSpaces + " " + "var=null");
|
||||||
} else {
|
} else {
|
||||||
@ -580,8 +528,8 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
}
|
}
|
||||||
} while (((oldFunctionsList.size() != before || step != "sums") && oldFunctionsList.size() > 1));
|
} while (((oldFunctionsList.size() != before || step != "sums") && oldFunctionsList.size() > 1));
|
||||||
}
|
}
|
||||||
if(oldFunctionsList.isEmpty()) {
|
if (oldFunctionsList.isEmpty()) {
|
||||||
setVariables(new Function[]{new Number(root, 0)});
|
setVariables(new Function[] { new Number(root, 0) });
|
||||||
} else {
|
} else {
|
||||||
setVariables(oldFunctionsList);
|
setVariables(oldFunctionsList);
|
||||||
}
|
}
|
||||||
@ -593,7 +541,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
}
|
}
|
||||||
Utils.debug.println(debugSpaces + "•Finished correcting classes.");
|
Utils.debug.println(debugSpaces + "•Finished correcting classes.");
|
||||||
|
|
||||||
String result = toString();
|
final String result = toString();
|
||||||
Utils.debug.println(debugSpaces + "•Result:" + result);
|
Utils.debug.println(debugSpaces + "•Result:" + result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -608,7 +556,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
if (functions.length > 1) {
|
if (functions.length > 1) {
|
||||||
return true;
|
return true;
|
||||||
} else if (functions.length == 1) {
|
} else if (functions.length == 1) {
|
||||||
Function f = functions[0];
|
final Function f = functions[0];
|
||||||
if (f.isSolved() == false) {
|
if (f.isSolved() == false) {
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
@ -620,28 +568,28 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Function> solveOneStep() throws Error {
|
public List<Function> solveOneStep() throws Error {
|
||||||
List<Function> ret = new ArrayList<>();
|
final List<Function> ret = new ArrayList<>();
|
||||||
if (functions.length == 1) {
|
if (functions.length == 1) {
|
||||||
if (functions[0].isSolved() || !parenthesisNeeded()) {
|
if (functions[0].isSolved() || !parenthesisNeeded()) {
|
||||||
ret.add(functions[0]);
|
ret.add(functions[0]);
|
||||||
return ret;
|
return ret;
|
||||||
} else {
|
} else {
|
||||||
List<Function> l = functions[0].solveOneStep();
|
final List<Function> l = functions[0].solveOneStep();
|
||||||
for (Function f : l) {
|
for (final Function f : l) {
|
||||||
if (f instanceof Number || f instanceof Variable) {
|
if (f instanceof Number || f instanceof Variable) {
|
||||||
ret.add(f);
|
ret.add(f);
|
||||||
} else {
|
} else {
|
||||||
ret.add(new Expression(root, new Function[]{f}));
|
ret.add(new Expression(root, new Function[] { f }));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
if (f.isSolved() == false) {
|
if (f.isSolved() == false) {
|
||||||
List<Function> partial = f.solveOneStep();
|
final List<Function> partial = f.solveOneStep();
|
||||||
for (Function fnc : partial) {
|
for (final Function fnc : partial) {
|
||||||
ret.add(new Expression(root, new Function[]{fnc}));
|
ret.add(new Expression(root, new Function[] { fnc }));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -651,7 +599,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void generateGraphics() {
|
public void generateGraphics() {
|
||||||
for (Function var : functions) {
|
for (final Function var : functions) {
|
||||||
var.setSmall(small);
|
var.setSmall(small);
|
||||||
var.generateGraphics();
|
var.generateGraphics();
|
||||||
}
|
}
|
||||||
@ -667,18 +615,16 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
parenthesisneeded = false;
|
parenthesisneeded = false;
|
||||||
} else {
|
} else {
|
||||||
if (functions.length == 1) {
|
if (functions.length == 1) {
|
||||||
Function f = functions[0];
|
final Function f = functions[0];
|
||||||
if (f instanceof Number || f instanceof Variable || f instanceof Expression || f instanceof Division || f instanceof Joke
|
if (f instanceof Number || f instanceof Variable || f instanceof Expression || f instanceof Division || f instanceof Joke || f instanceof Undefined || f instanceof Power || f instanceof Sine || f instanceof Cosine || f instanceof Tangent || f instanceof ArcSine || f instanceof ArcCosine || f instanceof ArcTangent) {
|
||||||
|| f instanceof Undefined || f instanceof Power || f instanceof Sine || f instanceof Cosine || f instanceof Tangent
|
|
||||||
|| f instanceof ArcSine || f instanceof ArcCosine || f instanceof ArcTangent) {
|
|
||||||
parenthesisneeded = false;
|
parenthesisneeded = false;
|
||||||
}
|
}
|
||||||
if (f instanceof Multiplication) {
|
if (f instanceof Multiplication) {
|
||||||
if (((Multiplication)f).getVariable1() instanceof Number) {
|
if (((Multiplication) f).getVariable1() instanceof Number) {
|
||||||
parenthesisneeded = !(((Multiplication)f).getVariable2() instanceof Variable);
|
parenthesisneeded = !(((Multiplication) f).getVariable2() instanceof Variable);
|
||||||
} else if (((Multiplication)f).getVariable2() instanceof Number) {
|
} else if (((Multiplication) f).getVariable2() instanceof Number) {
|
||||||
parenthesisneeded = !(((Multiplication)f).getVariable1() instanceof Variable);
|
parenthesisneeded = !(((Multiplication) f).getVariable1() instanceof Variable);
|
||||||
} else if (((Multiplication) f).getVariable1() instanceof Variable || ((Multiplication)f).getVariable2() instanceof Variable) {
|
} else if (((Multiplication) f).getVariable1() instanceof Variable || ((Multiplication) f).getVariable2() instanceof Variable) {
|
||||||
parenthesisneeded = false;
|
parenthesisneeded = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -690,26 +636,26 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
if (parenthesisNeeded() == false) {
|
if (parenthesisNeeded() == false) {
|
||||||
this.functions[0].draw(x, y);
|
functions[0].draw(x, y);
|
||||||
} else {
|
} else {
|
||||||
float miny = y;
|
final float miny = y;
|
||||||
float maxy = y + getHeight();
|
final float maxy = y + getHeight();
|
||||||
int h = getHeight();
|
final int h = getHeight();
|
||||||
x += 1;
|
x += 1;
|
||||||
PIDisplay.renderer.glDrawLine(x, y + 2, x + 2, y);
|
DisplayManager.renderer.glDrawLine(x, y + 2, x + 2, y);
|
||||||
PIDisplay.renderer.glDrawLine(x, y + 2, x, y + h - 3);
|
DisplayManager.renderer.glDrawLine(x, y + 2, x, y + h - 3);
|
||||||
PIDisplay.renderer.glDrawLine(x, y + h - 3, x + 2, y + h - 1);
|
DisplayManager.renderer.glDrawLine(x, y + h - 3, x + 2, y + h - 1);
|
||||||
x += 4;
|
x += 4;
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
float fheight = f.getHeight();
|
final float fheight = f.getHeight();
|
||||||
float y2 = miny + ((maxy - miny) / 2 - fheight / 2);
|
final float y2 = miny + ((maxy - miny) / 2 - fheight / 2);
|
||||||
f.draw(x, (int) y2);
|
f.draw(x, (int) y2);
|
||||||
x += f.getWidth();
|
x += f.getWidth();
|
||||||
}
|
}
|
||||||
x += 2;
|
x += 2;
|
||||||
PIDisplay.renderer.glDrawLine(x, y, x + 2, y + 2);
|
DisplayManager.renderer.glDrawLine(x, y, x + 2, y + 2);
|
||||||
PIDisplay.renderer.glDrawLine(x + 2, y + 2, x + 2, y + h - 3);
|
DisplayManager.renderer.glDrawLine(x + 2, y + 2, x + 2, y + h - 3);
|
||||||
PIDisplay.renderer.glDrawLine(x, y + h - 1, x + 2, y + h - 3);
|
DisplayManager.renderer.glDrawLine(x, y + h - 1, x + 2, y + h - 3);
|
||||||
x += 4;
|
x += 4;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -721,10 +667,10 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
|
|
||||||
private int calcWidth() {
|
private int calcWidth() {
|
||||||
if (parenthesisNeeded() == false) {
|
if (parenthesisNeeded() == false) {
|
||||||
return this.functions[0].getWidth();
|
return functions[0].getWidth();
|
||||||
} else {
|
} else {
|
||||||
int w = 0;
|
int w = 0;
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
w += f.getWidth();
|
w += f.getWidth();
|
||||||
}
|
}
|
||||||
return 1 + 4 + w + 2 + 4;
|
return 1 + 4 + w + 2 + 4;
|
||||||
@ -738,11 +684,11 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
|
|
||||||
private int calcHeight() {
|
private int calcHeight() {
|
||||||
if (initialParenthesis || functions.length == 1) {
|
if (initialParenthesis || functions.length == 1) {
|
||||||
return this.functions[0].getHeight();
|
return functions[0].getHeight();
|
||||||
} else {
|
} else {
|
||||||
Function tmin = null;
|
Function tmin = null;
|
||||||
Function tmax = null;
|
Function tmax = null;
|
||||||
for (Function t : functions) {
|
for (final Function t : functions) {
|
||||||
if (tmin == null || t.getLine() >= tmin.getLine()) {
|
if (tmin == null || t.getLine() >= tmin.getLine()) {
|
||||||
tmin = t;
|
tmin = t;
|
||||||
}
|
}
|
||||||
@ -750,8 +696,9 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
tmax = t;
|
tmax = t;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (tmin == null)
|
if (tmin == null) {
|
||||||
return Utils.getFontHeight(small);
|
return Utils.getFontHeight(small);
|
||||||
|
}
|
||||||
return tmin.getLine() + tmax.getHeight() - tmax.getLine();
|
return tmin.getLine() + tmax.getHeight() - tmax.getLine();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -763,16 +710,17 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
|
|
||||||
private int calcLine() {
|
private int calcLine() {
|
||||||
if (initialParenthesis || functions.length == 1) {
|
if (initialParenthesis || functions.length == 1) {
|
||||||
return this.functions[0].getLine();
|
return functions[0].getLine();
|
||||||
} else {
|
} else {
|
||||||
Function tl = null;
|
Function tl = null;
|
||||||
for (Function t : functions) {
|
for (final Function t : functions) {
|
||||||
if (tl == null || t.getLine() >= tl.getLine()) {
|
if (tl == null || t.getLine() >= tl.getLine()) {
|
||||||
tl = t;
|
tl = t;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (tl == null)
|
if (tl == null) {
|
||||||
return Utils.getFontHeight(small) / 2;
|
return Utils.getFontHeight(small) / 2;
|
||||||
|
}
|
||||||
return tl.getLine();
|
return tl.getLine();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -786,7 +734,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
vars = functions[0].toString();
|
vars = functions[0].toString();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
for (Function variable : functions) {
|
for (final Function variable : functions) {
|
||||||
if (variable != null) {
|
if (variable != null) {
|
||||||
vars += ", " + variable.toString();
|
vars += ", " + variable.toString();
|
||||||
}
|
}
|
||||||
@ -794,15 +742,15 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
vars = vars.substring(2);
|
vars = vars.substring(2);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return "("+vars+")";
|
return "(" + vars + ")";
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Expression) {
|
if (o instanceof Expression) {
|
||||||
Expression f = (Expression) o;
|
final Expression f = (Expression) o;
|
||||||
Function[] exprFuncs1 = functions;
|
final Function[] exprFuncs1 = functions;
|
||||||
Function[] exprFuncs2 = f.functions;
|
final Function[] exprFuncs2 = f.functions;
|
||||||
if (exprFuncs1.length == exprFuncs2.length) {
|
if (exprFuncs1.length == exprFuncs2.length) {
|
||||||
for (int i = 0; i < exprFuncs1.length; i++) {
|
for (int i = 0; i < exprFuncs1.length; i++) {
|
||||||
if (exprFuncs1[i].equals(exprFuncs2[i]) == false) {
|
if (exprFuncs1[i].equals(exprFuncs2[i]) == false) {
|
||||||
@ -812,7 +760,7 @@ public class Expression extends FunctionMultipleValues {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
} else if (o != null & getVariablesLength() == 1) {
|
} else if (o != null & getVariablesLength() == 1) {
|
||||||
Function f = (Function) o;
|
final Function f = (Function) o;
|
||||||
return (functions[0].equals(f));
|
return (functions[0].equals(f));
|
||||||
} else if (o == null & getVariablesLength() == 0) {
|
} else if (o == null & getVariablesLength() == 0) {
|
||||||
return true;
|
return true;
|
||||||
|
@ -15,7 +15,7 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
|
|
||||||
public FunctionMultipleValues(Function[] values) {
|
public FunctionMultipleValues(Function[] values) {
|
||||||
if (values.length > 0) {
|
if (values.length > 0) {
|
||||||
this.root = values[0].getRoot();
|
root = values[0].getRoot();
|
||||||
} else {
|
} else {
|
||||||
throw new NullPointerException("Nessun elemento nell'array. Impossibile ricavare il nodo root");
|
throw new NullPointerException("Nessun elemento nell'array. Impossibile ricavare il nodo root");
|
||||||
}
|
}
|
||||||
@ -39,8 +39,8 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void setVariables(final List<Function> value) {
|
public void setVariables(final List<Function> value) {
|
||||||
int vsize = value.size();
|
final int vsize = value.size();
|
||||||
Function[] tmp = new Function[vsize];
|
final Function[] tmp = new Function[vsize];
|
||||||
for (int i = 0; i < vsize; i++) {
|
for (int i = 0; i < vsize; i++) {
|
||||||
tmp[i] = value.get(i);
|
tmp[i] = value.get(i);
|
||||||
}
|
}
|
||||||
@ -60,7 +60,7 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void addFunctionToEnd(Function value) {
|
public void addFunctionToEnd(Function value) {
|
||||||
int index = functions.length;
|
final int index = functions.length;
|
||||||
setVariablesLength(index + 1);
|
setVariablesLength(index + 1);
|
||||||
functions[index] = value;
|
functions[index] = value;
|
||||||
}
|
}
|
||||||
@ -78,7 +78,7 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isSolved() {
|
public boolean isSolved() {
|
||||||
for (Function variable : functions) {
|
for (final Function variable : functions) {
|
||||||
if (!variable.isSolved()) {
|
if (!variable.isSolved()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -100,7 +100,7 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
public String toString() {
|
public String toString() {
|
||||||
// try {
|
// try {
|
||||||
// return solve().toString();
|
// return solve().toString();
|
||||||
return "TODO: fare una nuova alternativa a solve().toString()";
|
return "TODO: fare una nuova alternativa a solve().toString()";
|
||||||
// } catch (Error e) {
|
// } catch (Error e) {
|
||||||
// return e.id.toString();
|
// return e.id.toString();
|
||||||
// }
|
// }
|
||||||
@ -108,7 +108,7 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Function clone() {
|
public Function clone() {
|
||||||
Cloner cloner = new Cloner();
|
final Cloner cloner = new Cloner();
|
||||||
return cloner.deepClone(this);
|
return cloner.deepClone(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -119,7 +119,7 @@ public abstract class FunctionMultipleValues implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int hashCode() {
|
public int hashCode() {
|
||||||
return functions.hashCode()+883*getSymbol().hashCode();
|
return functions.hashCode() + 883 * getSymbol().hashCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -4,7 +4,7 @@ import java.util.ArrayList;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
@ -62,13 +62,13 @@ public abstract class FunctionTwoValues implements Function {
|
|||||||
@Override
|
@Override
|
||||||
public final ArrayList<Function> solveOneStep() throws Error {
|
public final ArrayList<Function> solveOneStep() throws Error {
|
||||||
final boolean solved = variable1.isSolved() & variable2.isSolved();
|
final boolean solved = variable1.isSolved() & variable2.isSolved();
|
||||||
ArrayList<Function> result = solved?solve():null;;
|
ArrayList<Function> result = solved ? solve() : null;;
|
||||||
|
|
||||||
if (result == null || result.isEmpty()) {
|
if (result == null || result.isEmpty()) {
|
||||||
result = new ArrayList<>();
|
result = new ArrayList<>();
|
||||||
|
|
||||||
ArrayList<Function> l1 = new ArrayList<>();
|
final ArrayList<Function> l1 = new ArrayList<>();
|
||||||
ArrayList<Function> l2 = new ArrayList<>();
|
final ArrayList<Function> l2 = new ArrayList<>();
|
||||||
if (variable1.isSolved()) {
|
if (variable1.isSolved()) {
|
||||||
l1.add(variable1);
|
l1.add(variable1);
|
||||||
} else {
|
} else {
|
||||||
@ -80,10 +80,10 @@ public abstract class FunctionTwoValues implements Function {
|
|||||||
l2.addAll(variable2.solveOneStep());
|
l2.addAll(variable2.solveOneStep());
|
||||||
}
|
}
|
||||||
|
|
||||||
Function[][] results = Utils.joinFunctionsResults(l1, l2);
|
final Function[][] results = Utils.joinFunctionsResults(l1, l2);
|
||||||
|
|
||||||
for (Function[] f : results) {
|
for (final Function[] f : results) {
|
||||||
result.add(NewInstance(this.root, f[0], f[1]));
|
result.add(NewInstance(root, f[0], f[1]));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -107,14 +107,14 @@ public abstract class FunctionTwoValues implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
int ln = getLine();
|
final int ln = getLine();
|
||||||
int dx = 0;
|
int dx = 0;
|
||||||
variable1.draw(dx + x, ln - variable1.getLine() + y);
|
variable1.draw(dx + x, ln - variable1.getLine() + y);
|
||||||
dx += 1+variable1.getWidth();
|
dx += 1 + variable1.getWidth();
|
||||||
if (drawSignum()) {
|
if (drawSignum()) {
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
Utils.getFont(small).use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawStringLeft(dx + x, ln - Utils.getFontHeight(small) / 2 + y, getSymbol());
|
DisplayManager.renderer.glDrawStringLeft(dx + x, ln - Utils.getFontHeight(small) / 2 + y, getSymbol());
|
||||||
dx += PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
dx += Utils.getFont(small).getStringWidth(getSymbol());
|
||||||
}
|
}
|
||||||
variable2.draw(dx + x, ln - variable2.getLine() + y);
|
variable2.draw(dx + x, ln - variable2.getLine() + y);
|
||||||
}
|
}
|
||||||
@ -144,12 +144,12 @@ public abstract class FunctionTwoValues implements Function {
|
|||||||
if (variable2 != null) {
|
if (variable2 != null) {
|
||||||
val2 = variable2.toString();
|
val2 = variable2.toString();
|
||||||
}
|
}
|
||||||
return val1+getSymbol()+val2;
|
return val1 + getSymbol() + val2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public FunctionTwoValues clone() {
|
public FunctionTwoValues clone() {
|
||||||
Cloner cloner = new Cloner();
|
final Cloner cloner = new Cloner();
|
||||||
return cloner.deepClone(this);
|
return cloner.deepClone(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -163,7 +163,7 @@ public abstract class FunctionTwoValues implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected int calcWidth() {
|
protected int calcWidth() {
|
||||||
return variable1.getWidth() + 1 + (drawSignum() ? PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol()) : 0) + variable2.getWidth();
|
return variable1.getWidth() + 1 + (drawSignum() ? Utils.getFont(small).getStringWidth(getSymbol()) : 0) + variable2.getWidth();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected int calcHeight() {
|
protected int calcHeight() {
|
||||||
@ -189,7 +189,7 @@ public abstract class FunctionTwoValues implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int hashCode() {
|
public int hashCode() {
|
||||||
return variable1.hashCode()+7*variable2.hashCode()+883*getSymbol().hashCode();
|
return variable1.hashCode() + 7 * variable2.hashCode() + 883 * getSymbol().hashCode();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -4,7 +4,7 @@ import java.util.List;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
@ -14,8 +14,8 @@ public class Joke implements Function {
|
|||||||
public static final byte FISH = 0;
|
public static final byte FISH = 0;
|
||||||
public static final byte TORNADO = 1;
|
public static final byte TORNADO = 1;
|
||||||
public static final byte SHARKNADO = 2;
|
public static final byte SHARKNADO = 2;
|
||||||
private static final String[] jokes = new String[]{"♓", "TORNADO", "SHARKNADO"};
|
private static final String[] jokes = new String[] { "♓", "TORNADO", "SHARKNADO" };
|
||||||
private static final int[] jokesFont = new int[]{4, -1, -1};
|
private static final int[] jokesFont = new int[] { 4, -1, -1 };
|
||||||
private final byte joke;
|
private final byte joke;
|
||||||
private final Calculator root;
|
private final Calculator root;
|
||||||
|
|
||||||
@ -46,29 +46,29 @@ public class Joke implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
RAWFont rf = PIDisplay.renderer.getCurrentFont();
|
final RAWFont rf = DisplayManager.renderer.getCurrentFont();
|
||||||
if (jokesFont[joke] >= 0) {
|
if (jokesFont[joke] >= 0) {
|
||||||
PIDisplay.renderer.glSetFont(PIDisplay.fonts[jokesFont[joke]]);
|
DisplayManager.renderer.glSetFont(DisplayManager.fonts[jokesFont[joke]]);
|
||||||
}
|
}
|
||||||
PIDisplay.renderer.glDrawStringLeft(x, y, jokes[joke]);
|
DisplayManager.renderer.glDrawStringLeft(x, y, jokes[joke]);
|
||||||
if (jokesFont[joke] >= 0) {
|
if (jokesFont[joke] >= 0) {
|
||||||
PIDisplay.renderer.glSetFont(rf);
|
DisplayManager.renderer.glSetFont(rf);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getWidth() {
|
public int getWidth() {
|
||||||
if (jokesFont[joke] >= 0) {
|
if (jokesFont[joke] >= 0) {
|
||||||
return PIDisplay.renderer.glGetStringWidth(PIDisplay.fonts[jokesFont[joke]], jokes[joke]);
|
return DisplayManager.renderer.glGetStringWidth(DisplayManager.fonts[jokesFont[joke]], jokes[joke]);
|
||||||
} else {
|
} else {
|
||||||
return PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), jokes[joke]);
|
return DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), jokes[joke]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getHeight() {
|
public int getHeight() {
|
||||||
if (jokesFont[joke] >= 0) {
|
if (jokesFont[joke] >= 0) {
|
||||||
return PIDisplay.fonts[jokesFont[joke]].charH;
|
return DisplayManager.fonts[jokesFont[joke]].charH;
|
||||||
} else {
|
} else {
|
||||||
return Utils.getFont(small).charH;
|
return Utils.getFont(small).charH;
|
||||||
}
|
}
|
||||||
@ -76,7 +76,7 @@ public class Joke implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getLine() {
|
public int getLine() {
|
||||||
return getHeight()/2;
|
return getHeight() / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -37,12 +37,24 @@ public class Multiplication extends FunctionTwoValues {
|
|||||||
if (variable1 instanceof Number & variable2 instanceof Number) {
|
if (variable1 instanceof Number & variable2 instanceof Number) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (SyntaxRule1.compare(this)) return true;
|
if (SyntaxRule1.compare(this)) {
|
||||||
if (NumberRule1.compare(this)) return true;
|
return true;
|
||||||
if (NumberRule2.compare(this)) return true;
|
}
|
||||||
if (NumberRule6.compare(this)) return true;
|
if (NumberRule1.compare(this)) {
|
||||||
if (ExponentRule15.compare(this)) return true;
|
return true;
|
||||||
if (MultiplicationMethod1.compare(this)) return true;
|
}
|
||||||
|
if (NumberRule2.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule6.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (ExponentRule15.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (MultiplicationMethod1.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -62,15 +74,15 @@ public class Multiplication extends FunctionTwoValues {
|
|||||||
} else if (MultiplicationMethod1.compare(this)) {
|
} else if (MultiplicationMethod1.compare(this)) {
|
||||||
result = MultiplicationMethod1.execute(this);
|
result = MultiplicationMethod1.execute(this);
|
||||||
} else if (variable1.isSolved() & variable2.isSolved()) {
|
} else if (variable1.isSolved() & variable2.isSolved()) {
|
||||||
result.add(((Number)variable1).multiply((Number)variable2));
|
result.add(((Number) variable1).multiply((Number) variable2));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean drawSignum() {
|
public boolean drawSignum() {
|
||||||
Function[] tmpVar = new Function[] { variable1, variable2 };
|
final Function[] tmpVar = new Function[] { variable1, variable2 };
|
||||||
boolean[] ok = new boolean[] { false, false };
|
final boolean[] ok = new boolean[] { false, false };
|
||||||
for (int val = 0; val < 2; val++) {
|
for (int val = 0; val < 2; val++) {
|
||||||
while (!ok[val]) {
|
while (!ok[val]) {
|
||||||
if (tmpVar[val] instanceof Division) {
|
if (tmpVar[val] instanceof Division) {
|
||||||
@ -136,7 +148,7 @@ public class Multiplication extends FunctionTwoValues {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Multiplication) {
|
if (o instanceof Multiplication) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
if (variable1.equals(f.variable1) && variable2.equals(f.variable2)) {
|
if (variable1.equals(f.variable1) && variable2.equals(f.variable2)) {
|
||||||
return true;
|
return true;
|
||||||
} else if (variable1.equals(f.variable2) && variable2.equals(f.variable1)) {
|
} else if (variable1.equals(f.variable2) && variable2.equals(f.variable1)) {
|
||||||
|
@ -5,7 +5,7 @@ import java.util.ArrayList;
|
|||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Errors;
|
import org.warp.picalculator.Errors;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
@ -34,15 +34,21 @@ public class Negative extends AnteriorFunction {
|
|||||||
variable.generateGraphics();
|
variable.generateGraphics();
|
||||||
|
|
||||||
height = getVariable().getHeight();
|
height = getVariable().getHeight();
|
||||||
width = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), "-") + getVariable().getWidth();
|
width = DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), "-") + getVariable().getWidth();
|
||||||
line = getVariable().getLine();
|
line = getVariable().getLine();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected boolean isSolvable() {
|
protected boolean isSolvable() {
|
||||||
if (variable instanceof Number) return true;
|
if (variable instanceof Number) {
|
||||||
if (ExpandRule1.compare(this)) return true;
|
return true;
|
||||||
if (ExpandRule5.compare(this)) return true;
|
}
|
||||||
|
if (ExpandRule1.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (ExpandRule5.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -58,24 +64,24 @@ public class Negative extends AnteriorFunction {
|
|||||||
result = ExpandRule5.execute(this);
|
result = ExpandRule5.execute(this);
|
||||||
} else if (variable.isSolved()) {
|
} else if (variable.isSolved()) {
|
||||||
try {
|
try {
|
||||||
Number var = (Number) getVariable();
|
final Number var = (Number) getVariable();
|
||||||
result.add(var.multiply(new Number(root, "-1")));
|
result.add(var.multiply(new Number(root, "-1")));
|
||||||
} catch(NullPointerException ex) {
|
} catch (final NullPointerException ex) {
|
||||||
throw new Error(Errors.ERROR);
|
throw new Error(Errors.ERROR);
|
||||||
} catch(NumberFormatException ex) {
|
} catch (final NumberFormatException ex) {
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
} catch(ArithmeticException ex) {
|
} catch (final ArithmeticException ex) {
|
||||||
throw new Error(Errors.NUMBER_TOO_SMALL);
|
throw new Error(Errors.NUMBER_TOO_SMALL);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
ArrayList<Function> l1 = new ArrayList<>();
|
final ArrayList<Function> l1 = new ArrayList<>();
|
||||||
if (variable.isSolved()) {
|
if (variable.isSolved()) {
|
||||||
l1.add(variable);
|
l1.add(variable);
|
||||||
} else {
|
} else {
|
||||||
l1.addAll(variable.solveOneStep());
|
l1.addAll(variable.solveOneStep());
|
||||||
}
|
}
|
||||||
|
|
||||||
for (Function f : l1) {
|
for (final Function f : l1) {
|
||||||
result.add(new Negative(root, f));
|
result.add(new Negative(root, f));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -100,7 +106,7 @@ public class Negative extends AnteriorFunction {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Negative) {
|
if (o instanceof Negative) {
|
||||||
return ((Negative)o).variable.equals(variable);
|
return ((Negative) o).variable.equals(variable);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -9,9 +9,8 @@ import java.util.List;
|
|||||||
import org.nevec.rjm.BigDecimalMath;
|
import org.nevec.rjm.BigDecimalMath;
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
import org.warp.picalculator.gui.graphicengine.RAWFont;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
import com.rits.cloning.Cloner;
|
import com.rits.cloning.Cloner;
|
||||||
@ -72,26 +71,26 @@ public class Number implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public Number add(Number f) {
|
public Number add(Number f) {
|
||||||
Number ret = new Number(this.root, getTerm().add(f.getTerm()));
|
final Number ret = new Number(root, getTerm().add(f.getTerm()));
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Number multiply(Number f) {
|
public Number multiply(Number f) {
|
||||||
Number ret = new Number(this.root, getTerm().multiply(f.getTerm()));
|
final Number ret = new Number(root, getTerm().multiply(f.getTerm()));
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Number divide(Number f) throws Error {
|
public Number divide(Number f) throws Error {
|
||||||
Number ret = new Number(this.root, BigDecimalMath.divideRound(getTerm(), f.getTerm()));
|
final Number ret = new Number(root, BigDecimalMath.divideRound(getTerm(), f.getTerm()));
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Number pow(Number f) throws Error {
|
public Number pow(Number f) throws Error {
|
||||||
Number ret = new Number(this.root, BigDecimal.ONE);
|
Number ret = new Number(root, BigDecimal.ONE);
|
||||||
if (Utils.isIntegerValue(f.term)) {
|
if (Utils.isIntegerValue(f.term)) {
|
||||||
final BigInteger bi = f.term.toBigInteger();
|
final BigInteger bi = f.term.toBigInteger();
|
||||||
for (BigInteger i = BigInteger.ZERO; i.compareTo(bi) < 0; i = i.add(BigInteger.ONE)) {
|
for (BigInteger i = BigInteger.ZERO; i.compareTo(bi) < 0; i = i.add(BigInteger.ONE)) {
|
||||||
ret = ret.multiply(new Number(this.root, getTerm()));
|
ret = ret.multiply(new Number(root, getTerm()));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
ret.term = BigDecimalMath.pow(term, f.term);
|
ret.term = BigDecimalMath.pow(term, f.term);
|
||||||
@ -101,20 +100,20 @@ public class Number implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
String sWith0 = getTerm().setScale(Utils.displayScale, Utils.scaleMode2).toPlainString();
|
final String sWith0 = getTerm().setScale(Utils.displayScale, Utils.scaleMode2).toPlainString();
|
||||||
String sExtendedWith0 = getTerm().toPlainString();
|
final String sExtendedWith0 = getTerm().toPlainString();
|
||||||
//Remove trailing zeroes. Thanks to Kent, http://stackoverflow.com/questions/14984664/remove-trailing-zero-in-java
|
//Remove trailing zeroes. Thanks to Kent, http://stackoverflow.com/questions/14984664/remove-trailing-zero-in-java
|
||||||
String s = sWith0.indexOf(".") < 0 ? sWith0 : sWith0.replaceAll("0*$", "").replaceAll("\\.$", "");
|
String s = sWith0.indexOf(".") < 0 ? sWith0 : sWith0.replaceAll("0*$", "").replaceAll("\\.$", "");
|
||||||
String sExtended = sExtendedWith0.indexOf(".") < 0 ? sExtendedWith0 : sExtendedWith0.replaceAll("0*$", "").replaceAll("\\.$", "");
|
final String sExtended = sExtendedWith0.indexOf(".") < 0 ? sExtendedWith0 : sExtendedWith0.replaceAll("0*$", "").replaceAll("\\.$", "");
|
||||||
|
|
||||||
if (sExtended.length() > s.length()) {
|
if (sExtended.length() > s.length()) {
|
||||||
s = s+"…";
|
s = s + "…";
|
||||||
}
|
}
|
||||||
|
|
||||||
if (root.exactMode == false) {
|
if (root.exactMode == false) {
|
||||||
String cuttedNumber = s.split("\\.")[0];
|
final String cuttedNumber = s.split("\\.")[0];
|
||||||
if (cuttedNumber.length() > 8) {
|
if (cuttedNumber.length() > 8) {
|
||||||
return cuttedNumber.substring(0, 1)+","+cuttedNumber.substring(1, 8)+"ℯ℮"+(cuttedNumber.length()-1);
|
return cuttedNumber.substring(0, 1) + "," + cuttedNumber.substring(1, 8) + "ℯ℮" + (cuttedNumber.length() - 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return s;
|
return s;
|
||||||
@ -131,7 +130,7 @@ public class Number implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
Utils.getFont(small).use(DisplayManager.display);
|
||||||
String t = toString();
|
String t = toString();
|
||||||
|
|
||||||
if (t.startsWith("-")) {
|
if (t.startsWith("-")) {
|
||||||
@ -144,20 +143,20 @@ public class Number implements Function {
|
|||||||
if (t.contains("ℯ℮")) {
|
if (t.contains("ℯ℮")) {
|
||||||
final RAWFont defaultf = Utils.getFont(small);
|
final RAWFont defaultf = Utils.getFont(small);
|
||||||
final RAWFont smallf = Utils.getFont(true);
|
final RAWFont smallf = Utils.getFont(true);
|
||||||
String s = t.substring(0, t.indexOf("ℯ℮")+2);
|
final String s = t.substring(0, t.indexOf("ℯ℮") + 2);
|
||||||
int sw = PIDisplay.renderer.glGetStringWidth(defaultf, s);
|
final int sw = defaultf.getStringWidth(s);
|
||||||
PIDisplay.renderer.glDrawStringLeft(x+1, y+smallf.charH-2, s);
|
DisplayManager.renderer.glDrawStringLeft(x + 1, y + smallf.getCharacterHeight() - 2, s);
|
||||||
PIDisplay.renderer.glSetFont(smallf);
|
smallf.use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawStringLeft(x+1+sw-3, y, t.substring(t.indexOf("ℯ℮")+2));
|
DisplayManager.renderer.glDrawStringLeft(x + 1 + sw - 3, y, t.substring(t.indexOf("ℯ℮") + 2));
|
||||||
} else {
|
} else {
|
||||||
PIDisplay.renderer.glDrawStringLeft(x+1, y, t);
|
DisplayManager.renderer.glDrawStringLeft(x + 1, y, t);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public int getHeight(boolean drawMinus) {
|
public int getHeight(boolean drawMinus) {
|
||||||
boolean beforedrawminus = this.drawMinus;
|
final boolean beforedrawminus = this.drawMinus;
|
||||||
this.drawMinus = drawMinus;
|
this.drawMinus = drawMinus;
|
||||||
int h = getHeight();
|
final int h = getHeight();
|
||||||
this.drawMinus = beforedrawminus;
|
this.drawMinus = beforedrawminus;
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
@ -168,14 +167,15 @@ public class Number implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private int calcHeight() {
|
private int calcHeight() {
|
||||||
String t = toString();
|
final String t = toString();
|
||||||
if (t.contains("ℯ℮")) {
|
if (t.contains("ℯ℮")) {
|
||||||
return Utils.getFontHeight(small)-2+Utils.getFontHeight(true);
|
return Utils.getFontHeight(small) - 2 + Utils.getFontHeight(true);
|
||||||
} else {
|
} else {
|
||||||
int h1 = Utils.getFontHeight(small);
|
final int h1 = Utils.getFontHeight(small);
|
||||||
return h1;
|
return h1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getWidth() {
|
public int getWidth() {
|
||||||
return width;
|
return width;
|
||||||
@ -193,11 +193,11 @@ public class Number implements Function {
|
|||||||
if (t.contains("ℯ℮")) {
|
if (t.contains("ℯ℮")) {
|
||||||
final RAWFont defaultf = Utils.getFont(small);
|
final RAWFont defaultf = Utils.getFont(small);
|
||||||
final RAWFont smallf = Utils.getFont(true);
|
final RAWFont smallf = Utils.getFont(true);
|
||||||
String s = t.substring(0, t.indexOf("ℯ℮")+2);
|
final String s = t.substring(0, t.indexOf("ℯ℮") + 2);
|
||||||
int sw = PIDisplay.renderer.glGetStringWidth(defaultf, s);
|
final int sw = defaultf.getStringWidth(s);
|
||||||
return 1+sw-3+PIDisplay.renderer.glGetStringWidth(smallf, t.substring(t.indexOf("ℯ℮")+2));
|
return 1 + sw - 3 + smallf.getStringWidth(t.substring(t.indexOf("ℯ℮") + 2));
|
||||||
} else {
|
} else {
|
||||||
return PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), t)+1;
|
return Utils.getFont(small).getStringWidth(t) + 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -207,9 +207,9 @@ public class Number implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private int calcLine() {
|
private int calcLine() {
|
||||||
String t = toString();
|
final String t = toString();
|
||||||
if (t.contains("ℯ℮")) {
|
if (t.contains("ℯ℮")) {
|
||||||
return (Utils.getFontHeight(small) / 2)-2+Utils.getFontHeight(true);
|
return (Utils.getFontHeight(small) / 2) - 2 + Utils.getFontHeight(true);
|
||||||
} else {
|
} else {
|
||||||
return Utils.getFontHeight(small) / 2;
|
return Utils.getFontHeight(small) / 2;
|
||||||
}
|
}
|
||||||
@ -217,7 +217,7 @@ public class Number implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Number clone() {
|
public Number clone() {
|
||||||
Cloner cloner = new Cloner();
|
final Cloner cloner = new Cloner();
|
||||||
return cloner.deepClone(this);
|
return cloner.deepClone(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -233,7 +233,7 @@ public class Number implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Function> solveOneStep() throws Error {
|
public List<Function> solveOneStep() throws Error {
|
||||||
List<Function> result = new ArrayList<>();
|
final List<Function> result = new ArrayList<>();
|
||||||
result.add(this);
|
result.add(this);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -247,9 +247,9 @@ public class Number implements Function {
|
|||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o != null & term != null) {
|
if (o != null & term != null) {
|
||||||
if (o instanceof Number) {
|
if (o instanceof Number) {
|
||||||
BigDecimal nav = ((Number) o).getTerm();
|
final BigDecimal nav = ((Number) o).getTerm();
|
||||||
boolean na1 = term.compareTo(BigDecimal.ZERO) == 0;
|
final boolean na1 = term.compareTo(BigDecimal.ZERO) == 0;
|
||||||
boolean na2 = nav.compareTo(BigDecimal.ZERO) == 0;
|
final boolean na2 = nav.compareTo(BigDecimal.ZERO) == 0;
|
||||||
if (na1 == na2) {
|
if (na1 == na2) {
|
||||||
if (na1 == true) {
|
if (na1 == true) {
|
||||||
return true;
|
return true;
|
||||||
@ -291,41 +291,33 @@ public class Number implements Function {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public LinkedList<BigInteger> getFactors()
|
public LinkedList<BigInteger> getFactors() {
|
||||||
{
|
|
||||||
BigInteger n = getTerm().toBigIntegerExact();
|
BigInteger n = getTerm().toBigIntegerExact();
|
||||||
BigInteger two = BigInteger.valueOf(2);
|
final BigInteger two = BigInteger.valueOf(2);
|
||||||
LinkedList<BigInteger> fs = new LinkedList<>();
|
final LinkedList<BigInteger> fs = new LinkedList<>();
|
||||||
|
|
||||||
if (n.compareTo(two) < 0)
|
if (n.compareTo(two) < 0) {
|
||||||
{
|
throw new IllegalArgumentException("must be greater than one");
|
||||||
throw new IllegalArgumentException("must be greater than one");
|
}
|
||||||
}
|
|
||||||
|
|
||||||
while (n.mod(two).equals(BigInteger.ZERO))
|
while (n.mod(two).equals(BigInteger.ZERO)) {
|
||||||
{
|
fs.add(two);
|
||||||
fs.add(two);
|
n = n.divide(two);
|
||||||
n = n.divide(two);
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if (n.compareTo(BigInteger.ONE) > 0)
|
if (n.compareTo(BigInteger.ONE) > 0) {
|
||||||
{
|
BigInteger f = BigInteger.valueOf(3);
|
||||||
BigInteger f = BigInteger.valueOf(3);
|
while (f.multiply(f).compareTo(n) <= 0) {
|
||||||
while (f.multiply(f).compareTo(n) <= 0)
|
if (n.mod(f).equals(BigInteger.ZERO)) {
|
||||||
{
|
fs.add(f);
|
||||||
if (n.mod(f).equals(BigInteger.ZERO))
|
n = n.divide(f);
|
||||||
{
|
} else {
|
||||||
fs.add(f);
|
f = f.add(two);
|
||||||
n = n.divide(f);
|
}
|
||||||
}
|
}
|
||||||
else
|
fs.add(n);
|
||||||
{
|
}
|
||||||
f = f.add(two);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
fs.add(n);
|
|
||||||
}
|
|
||||||
|
|
||||||
return fs;
|
return fs;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -34,13 +34,27 @@ public class Power extends FunctionTwoValues {
|
|||||||
if (variable1 instanceof Number & variable2 instanceof Number) {
|
if (variable1 instanceof Number & variable2 instanceof Number) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (UndefinedRule1.compare(this)) return true;
|
if (UndefinedRule1.compare(this)) {
|
||||||
if (ExponentRule1.compare(this)) return true;
|
return true;
|
||||||
if (ExponentRule2.compare(this)) return true;
|
}
|
||||||
if (ExponentRule3.compare(this)) return true;
|
if (ExponentRule1.compare(this)) {
|
||||||
if (ExponentRule4.compare(this)) return true;
|
return true;
|
||||||
if (FractionsRule4.compare(this)) return true;
|
}
|
||||||
if (FractionsRule5.compare(this)) return true;
|
if (ExponentRule2.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (ExponentRule3.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (ExponentRule4.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (FractionsRule4.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (FractionsRule5.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -54,12 +68,12 @@ public class Power extends FunctionTwoValues {
|
|||||||
|
|
||||||
height = variable1.getHeight() + variable2.getHeight() - 4;
|
height = variable1.getHeight() + variable2.getHeight() - 4;
|
||||||
line = variable2.getHeight() - 4 + variable1.getLine();
|
line = variable2.getHeight() - 4 + variable1.getLine();
|
||||||
width = getVariable1().getWidth() + getVariable2().getWidth()+1;
|
width = getVariable1().getWidth() + getVariable2().getWidth() + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ArrayList<Function> solve() throws Error {
|
public ArrayList<Function> solve() throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
if (UndefinedRule1.compare(this)) {
|
if (UndefinedRule1.compare(this)) {
|
||||||
result.addAll(UndefinedRule1.execute(this));
|
result.addAll(UndefinedRule1.execute(this));
|
||||||
} else if (ExponentRule1.compare(this)) {
|
} else if (ExponentRule1.compare(this)) {
|
||||||
@ -75,7 +89,7 @@ public class Power extends FunctionTwoValues {
|
|||||||
} else if (FractionsRule5.compare(this)) {
|
} else if (FractionsRule5.compare(this)) {
|
||||||
result.addAll(FractionsRule5.execute(this));
|
result.addAll(FractionsRule5.execute(this));
|
||||||
} else if (variable1 instanceof Number & variable2 instanceof Number) {
|
} else if (variable1 instanceof Number & variable2 instanceof Number) {
|
||||||
result.add(((Number)variable1).pow((Number)variable2));
|
result.add(((Number) variable1).pow((Number) variable2));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -110,7 +124,7 @@ public class Power extends FunctionTwoValues {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Power) {
|
if (o instanceof Power) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
@ -5,7 +5,7 @@ import java.math.BigInteger;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
|
|
||||||
@ -47,8 +47,8 @@ public class Root extends FunctionTwoValues {
|
|||||||
try {
|
try {
|
||||||
Number exponent = new Number(root, BigDecimal.ONE);
|
Number exponent = new Number(root, BigDecimal.ONE);
|
||||||
exponent = exponent.divide((Number) variable1);
|
exponent = exponent.divide((Number) variable1);
|
||||||
Number resultVal = ((Number)variable2).pow(exponent);
|
final Number resultVal = ((Number) variable2).pow(exponent);
|
||||||
Number originalVariable = resultVal.pow(new Number(root, 2));
|
final Number originalVariable = resultVal.pow(new Number(root, 2));
|
||||||
if (originalVariable.equals(variable2)) {
|
if (originalVariable.equals(variable2)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -56,7 +56,7 @@ public class Root extends FunctionTwoValues {
|
|||||||
ex.printStackTrace();
|
ex.printStackTrace();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (variable1 instanceof Number && ((Number)variable1).equals(new Number(root, 2))) {
|
if (variable1 instanceof Number && ((Number) variable1).equals(new Number(root, 2))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
@ -64,18 +64,18 @@ public class Root extends FunctionTwoValues {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ArrayList<Function> solve() throws Error {
|
public ArrayList<Function> solve() throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
if (root.exactMode) {
|
if (root.exactMode) {
|
||||||
if (variable1 instanceof Number && ((Number)variable1).equals(new Number(root, 2))) {
|
if (variable1 instanceof Number && ((Number) variable1).equals(new Number(root, 2))) {
|
||||||
result.add(new RootSquare(root, variable2));
|
result.add(new RootSquare(root, variable2));
|
||||||
} else {
|
} else {
|
||||||
Number exponent = new Number(root, BigInteger.ONE);
|
Number exponent = new Number(root, BigInteger.ONE);
|
||||||
exponent = exponent.divide((Number) variable1);
|
exponent = exponent.divide((Number) variable1);
|
||||||
result.add(((Number)variable2).pow(exponent));
|
result.add(((Number) variable2).pow(exponent));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
Number exp = (Number) variable1;
|
final Number exp = (Number) variable1;
|
||||||
Number numb = (Number) variable2;
|
final Number numb = (Number) variable2;
|
||||||
|
|
||||||
result.add(numb.pow(new Number(root, 1).divide(exp)));
|
result.add(numb.pow(new Number(root, 1).divide(exp)));
|
||||||
}
|
}
|
||||||
@ -88,20 +88,20 @@ public class Root extends FunctionTwoValues {
|
|||||||
// glFillRect(x,y,width,height);
|
// glFillRect(x,y,width,height);
|
||||||
// glColor3f(0, 0, 0);
|
// glColor3f(0, 0, 0);
|
||||||
|
|
||||||
int w1 = getVariable2().getWidth();
|
final int w1 = getVariable2().getWidth();
|
||||||
int h1 = getVariable2().getHeight();
|
final int h1 = getVariable2().getHeight();
|
||||||
int w2 = getVariable1().getWidth();
|
final int w2 = getVariable1().getWidth();
|
||||||
int h2 = getVariable1().getHeight();
|
final int h2 = getVariable1().getHeight();
|
||||||
int height = getHeight();
|
final int height = getHeight();
|
||||||
int hh = (int) Math.ceil((double) h1 / 2);
|
final int hh = (int) Math.ceil((double) h1 / 2);
|
||||||
|
|
||||||
getVariable1().draw(x + 1, y);
|
getVariable1().draw(x + 1, y);
|
||||||
getVariable2().draw(x + 1 + w2 + 2, y + h2 - 2);
|
getVariable2().draw(x + 1 + w2 + 2, y + h2 - 2);
|
||||||
|
|
||||||
PIDisplay.renderer.glDrawLine(x + 1 + w2 - 2, y + height - 3, x + 1 + w2, y + height);
|
DisplayManager.renderer.glDrawLine(x + 1 + w2 - 2, y + height - 3, x + 1 + w2, y + height);
|
||||||
PIDisplay.renderer.glDrawLine(x + 1 + w2, y + height - 1 - hh, x + 1 + w2, y + height - 1);
|
DisplayManager.renderer.glDrawLine(x + 1 + w2, y + height - 1 - hh, x + 1 + w2, y + height - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 1 + w2 + 1, y + height - 2 - h1, x + 1 + w2 + 1, y + height - 1 - hh - 1);
|
DisplayManager.renderer.glDrawLine(x + 1 + w2 + 1, y + height - 2 - h1, x + 1 + w2 + 1, y + height - 1 - hh - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 1 + w2 + 1, y + height - h1 - 2, x + 1 + w2 + 2 + w1 + 1, y + height - h1 - 2);
|
DisplayManager.renderer.glDrawLine(x + 1 + w2 + 1, y + height - h1 - 2, x + 1 + w2 + 2 + w1 + 1, y + height - h1 - 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -122,7 +122,7 @@ public class Root extends FunctionTwoValues {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Root) {
|
if (o instanceof Root) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
@ -43,8 +43,8 @@ public class RootSquare extends AnteriorFunction {
|
|||||||
try {
|
try {
|
||||||
Number exponent = new Number(root, BigInteger.ONE);
|
Number exponent = new Number(root, BigInteger.ONE);
|
||||||
exponent = exponent.divide(new Number(root, 2));
|
exponent = exponent.divide(new Number(root, 2));
|
||||||
Number resultVal = ((Number)variable).pow(exponent);
|
final Number resultVal = ((Number) variable).pow(exponent);
|
||||||
Number originalVariable = resultVal.pow(new Number(root, 2));
|
final Number originalVariable = resultVal.pow(new Number(root, 2));
|
||||||
if (originalVariable.equals(variable)) {
|
if (originalVariable.equals(variable)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -57,14 +57,14 @@ public class RootSquare extends AnteriorFunction {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ArrayList<Function> solve() throws Error {
|
public ArrayList<Function> solve() throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
if (root.exactMode) {
|
if (root.exactMode) {
|
||||||
Number exponent = new Number(root, BigInteger.ONE);
|
Number exponent = new Number(root, BigInteger.ONE);
|
||||||
exponent = exponent.divide(new Number(root, 2));
|
exponent = exponent.divide(new Number(root, 2));
|
||||||
result.add(((Number)variable).pow(exponent));
|
result.add(((Number) variable).pow(exponent));
|
||||||
} else {
|
} else {
|
||||||
Number exp = new Number(root, 2);
|
final Number exp = new Number(root, 2);
|
||||||
Number numb = (Number) variable;
|
final Number numb = (Number) variable;
|
||||||
|
|
||||||
result.add(numb.pow(new Number(root, 1).divide(exp)));
|
result.add(numb.pow(new Number(root, 1).divide(exp)));
|
||||||
}
|
}
|
||||||
|
@ -35,14 +35,30 @@ public class Subtraction extends FunctionTwoValues {
|
|||||||
if (variable1 instanceof Number & variable2 instanceof Number) {
|
if (variable1 instanceof Number & variable2 instanceof Number) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (VariableRule1.compare(this)) return true;
|
if (VariableRule1.compare(this)) {
|
||||||
if (VariableRule2.compare(this)) return true;
|
return true;
|
||||||
if (VariableRule3.compare(this)) return true;
|
}
|
||||||
if (NumberRule3.compare(this)) return true;
|
if (VariableRule2.compare(this)) {
|
||||||
if (ExpandRule1.compare(this)) return true;
|
return true;
|
||||||
if (ExpandRule5.compare(this)) return true;
|
}
|
||||||
if (NumberRule5.compare(this)) return true;
|
if (VariableRule3.compare(this)) {
|
||||||
if (SumMethod1.compare(this)) return true;
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule3.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (ExpandRule1.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (ExpandRule5.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule5.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (SumMethod1.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -66,7 +82,7 @@ public class Subtraction extends FunctionTwoValues {
|
|||||||
} else if (SumMethod1.compare(this)) {
|
} else if (SumMethod1.compare(this)) {
|
||||||
result = SumMethod1.execute(this);
|
result = SumMethod1.execute(this);
|
||||||
} else if (variable1.isSolved() & variable2.isSolved()) {
|
} else if (variable1.isSolved() & variable2.isSolved()) {
|
||||||
result.add(((Number)variable1).add(((Number)variable2).multiply(new Number(root, "-1"))));
|
result.add(((Number) variable1).add(((Number) variable2).multiply(new Number(root, "-1"))));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -74,7 +90,7 @@ public class Subtraction extends FunctionTwoValues {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Subtraction) {
|
if (o instanceof Subtraction) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
@ -6,7 +6,7 @@ import java.util.ArrayList;
|
|||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Errors;
|
import org.warp.picalculator.Errors;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
import org.warp.picalculator.math.rules.NumberRule3;
|
import org.warp.picalculator.math.rules.NumberRule3;
|
||||||
@ -39,14 +39,30 @@ public class Sum extends FunctionTwoValues {
|
|||||||
if (variable1 instanceof Number & variable2 instanceof Number) {
|
if (variable1 instanceof Number & variable2 instanceof Number) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (SyntaxRule2.compare(this)) return true;
|
if (SyntaxRule2.compare(this)) {
|
||||||
if (VariableRule1.compare(this)) return true;
|
return true;
|
||||||
if (VariableRule2.compare(this)) return true;
|
}
|
||||||
if (VariableRule3.compare(this)) return true;
|
if (VariableRule1.compare(this)) {
|
||||||
if (NumberRule3.compare(this)) return true;
|
return true;
|
||||||
if (NumberRule5.compare(this)) return true;
|
}
|
||||||
if (NumberRule7.compare(this)) return true;
|
if (VariableRule2.compare(this)) {
|
||||||
if (SumMethod1.compare(this)) return true;
|
return true;
|
||||||
|
}
|
||||||
|
if (VariableRule3.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule3.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule5.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule7.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (SumMethod1.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -74,18 +90,18 @@ public class Sum extends FunctionTwoValues {
|
|||||||
result = SumMethod1.execute(this);
|
result = SumMethod1.execute(this);
|
||||||
} else if (variable1.isSolved() & variable2.isSolved()) {
|
} else if (variable1.isSolved() & variable2.isSolved()) {
|
||||||
if ((root.getChild().equals(this))) {
|
if ((root.getChild().equals(this))) {
|
||||||
if (((Number)variable1).term.compareTo(new BigDecimal(2)) == 0 && ((Number)variable2).term.compareTo(new BigDecimal(2)) == 0) {
|
if (((Number) variable1).term.compareTo(new BigDecimal(2)) == 0 && ((Number) variable2).term.compareTo(new BigDecimal(2)) == 0) {
|
||||||
result.add(new Joke(root, Joke.FISH));
|
result.add(new Joke(root, Joke.FISH));
|
||||||
return result;
|
return result;
|
||||||
} else if (((Number)variable1).term.compareTo(new BigDecimal(20)) == 0 && ((Number)variable2).term.compareTo(new BigDecimal(20)) == 0) {
|
} else if (((Number) variable1).term.compareTo(new BigDecimal(20)) == 0 && ((Number) variable2).term.compareTo(new BigDecimal(20)) == 0) {
|
||||||
result.add(new Joke(root, Joke.TORNADO));
|
result.add(new Joke(root, Joke.TORNADO));
|
||||||
return result;
|
return result;
|
||||||
} else if (((Number)variable1).term.compareTo(new BigDecimal(29)) == 0 && ((Number)variable2).term.compareTo(new BigDecimal(29)) == 0) {
|
} else if (((Number) variable1).term.compareTo(new BigDecimal(29)) == 0 && ((Number) variable2).term.compareTo(new BigDecimal(29)) == 0) {
|
||||||
result.add(new Joke(root, Joke.SHARKNADO));
|
result.add(new Joke(root, Joke.SHARKNADO));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
result.add(((Number)variable1).add((Number)variable2));
|
result.add(((Number) variable1).add((Number) variable2));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -113,14 +129,14 @@ public class Sum extends FunctionTwoValues {
|
|||||||
int dx = 0;
|
int dx = 0;
|
||||||
dx += variable1.getWidth();
|
dx += variable1.getWidth();
|
||||||
dx += 1;
|
dx += 1;
|
||||||
dx += PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
dx += DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
||||||
return dx += variable2.getWidth();
|
return dx += variable2.getWidth();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Sum) {
|
if (o instanceof Sum) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
if (variable1.equals(f.variable1) && variable2.equals(f.variable2)) {
|
if (variable1.equals(f.variable1) && variable2.equals(f.variable2)) {
|
||||||
return true;
|
return true;
|
||||||
} else if (variable1.equals(f.variable2) && variable2.equals(f.variable1)) {
|
} else if (variable1.equals(f.variable2) && variable2.equals(f.variable1)) {
|
||||||
|
@ -5,7 +5,7 @@ import java.util.ArrayList;
|
|||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Errors;
|
import org.warp.picalculator.Errors;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.MathematicalSymbols;
|
import org.warp.picalculator.math.MathematicalSymbols;
|
||||||
@ -35,10 +35,18 @@ public class SumSubtraction extends FunctionTwoValues {
|
|||||||
if (variable1 instanceof Number & variable2 instanceof Number) {
|
if (variable1 instanceof Number & variable2 instanceof Number) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (NumberRule3.compare(this)) return true;
|
if (NumberRule3.compare(this)) {
|
||||||
if (ExpandRule1.compare(this)) return true;
|
return true;
|
||||||
if (NumberRule4.compare(this)) return true;
|
}
|
||||||
if (NumberRule5.compare(this)) return true;
|
if (ExpandRule1.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule4.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
if (NumberRule5.compare(this)) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -57,8 +65,8 @@ public class SumSubtraction extends FunctionTwoValues {
|
|||||||
} else if (NumberRule5.compare(this)) {
|
} else if (NumberRule5.compare(this)) {
|
||||||
result = NumberRule5.execute(this);
|
result = NumberRule5.execute(this);
|
||||||
} else if (variable1.isSolved() & variable2.isSolved()) {
|
} else if (variable1.isSolved() & variable2.isSolved()) {
|
||||||
result.add(((Number)variable1).add((Number)variable2));
|
result.add(((Number) variable1).add((Number) variable2));
|
||||||
result.add(((Number)variable1).add(((Number)variable2).multiply(new Number(root, "-1"))));
|
result.add(((Number) variable1).add(((Number) variable2).multiply(new Number(root, "-1"))));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -82,14 +90,14 @@ public class SumSubtraction extends FunctionTwoValues {
|
|||||||
// glFillRect(x,y,width,height);
|
// glFillRect(x,y,width,height);
|
||||||
// glColor3f(0, 0, 0);
|
// glColor3f(0, 0, 0);
|
||||||
|
|
||||||
int ln = getLine();
|
final int ln = getLine();
|
||||||
int dx = 0;
|
int dx = 0;
|
||||||
variable1.draw(dx + x, ln - variable1.getLine() + y);
|
variable1.draw(dx + x, ln - variable1.getLine() + y);
|
||||||
dx += variable1.getWidth();
|
dx += variable1.getWidth();
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
DisplayManager.renderer.glSetFont(Utils.getFont(small));
|
||||||
dx += 1;
|
dx += 1;
|
||||||
PIDisplay.renderer.glDrawStringLeft(dx + x, ln - Utils.getFontHeight(small) / 2 + y, getSymbol());
|
DisplayManager.renderer.glDrawStringLeft(dx + x, ln - Utils.getFontHeight(small) / 2 + y, getSymbol());
|
||||||
dx += PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
dx += DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
||||||
variable2.draw(dx + x, ln - variable2.getLine() + y);
|
variable2.draw(dx + x, ln - variable2.getLine() + y);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -103,14 +111,14 @@ public class SumSubtraction extends FunctionTwoValues {
|
|||||||
int dx = 0;
|
int dx = 0;
|
||||||
dx += variable1.getWidth();
|
dx += variable1.getWidth();
|
||||||
dx += 1;
|
dx += 1;
|
||||||
dx += PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
dx += DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), getSymbol());
|
||||||
return dx += variable2.getWidth();
|
return dx += variable2.getWidth();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof SumSubtraction) {
|
if (o instanceof SumSubtraction) {
|
||||||
FunctionTwoValues f = (FunctionTwoValues) o;
|
final FunctionTwoValues f = (FunctionTwoValues) o;
|
||||||
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
return variable1.equals(f.variable1) && variable2.equals(f.variable2);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
@ -4,7 +4,7 @@ import java.util.List;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
import org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
@ -36,15 +36,15 @@ public class Undefined implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void generateGraphics() {
|
public void generateGraphics() {
|
||||||
width = PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), "UNDEFINED");
|
width = DisplayManager.renderer.glGetStringWidth(Utils.getFont(small), "UNDEFINED");
|
||||||
height = Utils.getFontHeight(small);
|
height = Utils.getFontHeight(small);
|
||||||
line = height/2;
|
line = height / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
DisplayManager.renderer.glSetFont(Utils.getFont(small));
|
||||||
PIDisplay.renderer.glDrawStringLeft(x, y, "UNDEFINED");
|
DisplayManager.renderer.glDrawStringLeft(x, y, "UNDEFINED");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -5,7 +5,7 @@ import java.util.List;
|
|||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.Utils;
|
import org.warp.picalculator.Utils;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
|
|
||||||
import com.rits.cloning.Cloner;
|
import com.rits.cloning.Cloner;
|
||||||
@ -50,7 +50,7 @@ public class Variable implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return ""+getChar();
|
return "" + getChar();
|
||||||
}
|
}
|
||||||
|
|
||||||
// public void draw(int x, int y, PIDisplay g, boolean small, boolean drawMinus) {
|
// public void draw(int x, int y, PIDisplay g, boolean small, boolean drawMinus) {
|
||||||
@ -62,8 +62,8 @@ public class Variable implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
PIDisplay.renderer.glSetFont(Utils.getFont(small));
|
Utils.getFont(small).use(DisplayManager.display);
|
||||||
PIDisplay.renderer.glDrawStringLeft(x+1, y, toString());
|
DisplayManager.renderer.glDrawStringLeft(x + 1, y, toString());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -72,7 +72,7 @@ public class Variable implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private int calcHeight() {
|
private int calcHeight() {
|
||||||
int h1 = Utils.getFontHeight(small);
|
final int h1 = Utils.getFontHeight(small);
|
||||||
return h1;
|
return h1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -82,7 +82,7 @@ public class Variable implements Function {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public int calcWidth() {
|
public int calcWidth() {
|
||||||
return PIDisplay.renderer.glGetStringWidth(Utils.getFont(small), toString())+1;
|
return Utils.getFont(small).getStringWidth(toString()) + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -106,7 +106,7 @@ public class Variable implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Variable clone() {
|
public Variable clone() {
|
||||||
Cloner cloner = new Cloner();
|
final Cloner cloner = new Cloner();
|
||||||
return cloner.deepClone(this);
|
return cloner.deepClone(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -122,7 +122,7 @@ public class Variable implements Function {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Function> solveOneStep() throws Error {
|
public List<Function> solveOneStep() throws Error {
|
||||||
List<Function> result = new ArrayList<>();
|
final List<Function> result = new ArrayList<>();
|
||||||
result.add(this);
|
result.add(this);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -21,7 +21,7 @@ import com.rits.cloning.Cloner;
|
|||||||
public class Equation extends FunctionTwoValues {
|
public class Equation extends FunctionTwoValues {
|
||||||
|
|
||||||
public Equation(Calculator root, Function value1, Function value2) {
|
public Equation(Calculator root, Function value1, Function value2) {
|
||||||
super(root, value1,value2);
|
super(root, value1, value2);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -47,12 +47,12 @@ public class Equation extends FunctionTwoValues {
|
|||||||
if (variable1 == null || variable2 == null) {
|
if (variable1 == null || variable2 == null) {
|
||||||
throw new Error(Errors.SYNTAX_ERROR);
|
throw new Error(Errors.SYNTAX_ERROR);
|
||||||
}
|
}
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
if (variable1.isSolved() & variable2.isSolved()) {
|
if (variable1.isSolved() & variable2.isSolved()) {
|
||||||
if (((Number)variable2).getTerm().compareTo(new BigDecimal(0)) == 0) {
|
if (((Number) variable2).getTerm().compareTo(new BigDecimal(0)) == 0) {
|
||||||
result.add(this);
|
result.add(this);
|
||||||
} else {
|
} else {
|
||||||
Equation e = new Equation(root, null, null);
|
final Equation e = new Equation(root, null, null);
|
||||||
e.setVariable1(new Subtraction(root, variable1, variable2));
|
e.setVariable1(new Subtraction(root, variable1, variable2));
|
||||||
e.setVariable2(new Number(root, "0"));
|
e.setVariable2(new Number(root, "0"));
|
||||||
result.add(e);
|
result.add(e);
|
||||||
@ -63,7 +63,7 @@ public class Equation extends FunctionTwoValues {
|
|||||||
|
|
||||||
public List<Function> solve(char variableCharacter) {
|
public List<Function> solve(char variableCharacter) {
|
||||||
@SuppressWarnings("unused")
|
@SuppressWarnings("unused")
|
||||||
ArrayList<Equation> e;
|
final ArrayList<Equation> e;
|
||||||
//TODO: WORK IN PROGRESS.
|
//TODO: WORK IN PROGRESS.
|
||||||
//TODO: Finire. Fare in modo che risolva i passaggi fino a che non ce ne sono più
|
//TODO: Finire. Fare in modo che risolva i passaggi fino a che non ce ne sono più
|
||||||
return null;
|
return null;
|
||||||
@ -72,14 +72,14 @@ public class Equation extends FunctionTwoValues {
|
|||||||
//WORK IN PROGRESS
|
//WORK IN PROGRESS
|
||||||
public ArrayList<Equation> solveStep(char charIncognita) {
|
public ArrayList<Equation> solveStep(char charIncognita) {
|
||||||
ArrayList<Equation> result = new ArrayList<>();
|
ArrayList<Equation> result = new ArrayList<>();
|
||||||
result.add(this.clone());
|
result.add(clone());
|
||||||
for (SolveMethod t : SolveMethod.techniques) {
|
for (final SolveMethod t : SolveMethod.techniques) {
|
||||||
ArrayList<Equation> newResults = new ArrayList<>();
|
final ArrayList<Equation> newResults = new ArrayList<>();
|
||||||
final int sz = result.size();
|
final int sz = result.size();
|
||||||
for (int n = 0; n < sz; n++) {
|
for (int n = 0; n < sz; n++) {
|
||||||
newResults.addAll(t.solve(result.get(n)));
|
newResults.addAll(t.solve(result.get(n)));
|
||||||
}
|
}
|
||||||
Set<Equation> hs = new HashSet<>();
|
final Set<Equation> hs = new HashSet<>();
|
||||||
hs.addAll(newResults);
|
hs.addAll(newResults);
|
||||||
newResults.clear();
|
newResults.clear();
|
||||||
newResults.addAll(hs);
|
newResults.addAll(hs);
|
||||||
@ -91,8 +91,14 @@ public class Equation extends FunctionTwoValues {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Equation clone() {
|
public Equation clone() {
|
||||||
Cloner cloner = new Cloner();
|
final Cloner cloner = new Cloner();
|
||||||
return cloner.deepClone(this);
|
return cloner.deepClone(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
@ -4,7 +4,7 @@ import java.util.ArrayList;
|
|||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.gui.PIDisplay;
|
import org.warp.picalculator.gui.DisplayManager;
|
||||||
import org.warp.picalculator.math.Calculator;
|
import org.warp.picalculator.math.Calculator;
|
||||||
import org.warp.picalculator.math.functions.Expression;
|
import org.warp.picalculator.math.functions.Expression;
|
||||||
import org.warp.picalculator.math.functions.Function;
|
import org.warp.picalculator.math.functions.Function;
|
||||||
@ -19,7 +19,7 @@ public class EquationsSystem extends FunctionMultipleValues {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public EquationsSystem(Calculator root, Function value) {
|
public EquationsSystem(Calculator root, Function value) {
|
||||||
super(root, new Function[]{value});
|
super(root, new Function[] { value });
|
||||||
}
|
}
|
||||||
|
|
||||||
public EquationsSystem(Calculator root, Function[] value) {
|
public EquationsSystem(Calculator root, Function[] value) {
|
||||||
@ -41,28 +41,28 @@ public class EquationsSystem extends FunctionMultipleValues {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<Function> solveOneStep() throws Error {
|
public List<Function> solveOneStep() throws Error {
|
||||||
List<Function> ret = new ArrayList<>();
|
final List<Function> ret = new ArrayList<>();
|
||||||
if (functions.length == 1) {
|
if (functions.length == 1) {
|
||||||
if (functions[0].isSolved()) {
|
if (functions[0].isSolved()) {
|
||||||
ret.add(functions[0]);
|
ret.add(functions[0]);
|
||||||
return ret;
|
return ret;
|
||||||
} else {
|
} else {
|
||||||
List<Function> l = functions[0].solveOneStep();
|
final List<Function> l = functions[0].solveOneStep();
|
||||||
for (Function f : l) {
|
for (final Function f : l) {
|
||||||
if (f instanceof Number) {
|
if (f instanceof Number) {
|
||||||
ret.add(f);
|
ret.add(f);
|
||||||
} else {
|
} else {
|
||||||
ret.add(new Expression(this.root, new Function[]{f}));
|
ret.add(new Expression(root, new Function[] { f }));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
if (f.isSolved() == false) {
|
if (f.isSolved() == false) {
|
||||||
List<Function> partial = f.solveOneStep();
|
final List<Function> partial = f.solveOneStep();
|
||||||
for (Function fnc : partial) {
|
for (final Function fnc : partial) {
|
||||||
ret.add(new Expression(this.root, new Function[]{fnc}));
|
ret.add(new Expression(root, new Function[] { fnc }));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -72,13 +72,13 @@ public class EquationsSystem extends FunctionMultipleValues {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void generateGraphics() {
|
public void generateGraphics() {
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
f.setSmall(false);
|
f.setSmall(false);
|
||||||
f.generateGraphics();
|
f.generateGraphics();
|
||||||
}
|
}
|
||||||
|
|
||||||
width = 0;
|
width = 0;
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
if (f.getWidth() > width) {
|
if (f.getWidth() > width) {
|
||||||
width = f.getWidth();
|
width = f.getWidth();
|
||||||
}
|
}
|
||||||
@ -86,35 +86,34 @@ public class EquationsSystem extends FunctionMultipleValues {
|
|||||||
width += 5;
|
width += 5;
|
||||||
|
|
||||||
height = 3;
|
height = 3;
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
height += f.getHeight()+spacing;
|
height += f.getHeight() + spacing;
|
||||||
}
|
}
|
||||||
height = height - spacing + 2;
|
height = height - spacing + 2;
|
||||||
|
|
||||||
line = height/2;
|
line = height / 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
|
|
||||||
final int h = this.getHeight() - 1;
|
final int h = getHeight() - 1;
|
||||||
final int marginTop = 3;
|
final int marginTop = 3;
|
||||||
final int marginBottom = (h - 3 - 2) / 2 + marginTop;
|
final int marginBottom = (h - 3 - 2) / 2 + marginTop;
|
||||||
final int spazioSopra = h - marginBottom;
|
final int spazioSopra = h - marginBottom;
|
||||||
int dy = marginTop;
|
int dy = marginTop;
|
||||||
for (Function f : functions) {
|
for (final Function f : functions) {
|
||||||
f.draw(x + 5, y + dy);
|
f.draw(x + 5, y + dy);
|
||||||
dy+=f.getHeight()+spacing;
|
dy += f.getHeight() + spacing;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DisplayManager.renderer.glDrawLine(x + 2, y + 0, x + 3, y + 0);
|
||||||
PIDisplay.renderer.glDrawLine(x + 2, y + 0, x + 3, y + 0);
|
DisplayManager.renderer.glDrawLine(x + 1, y + 1, x + 1, y + marginBottom / 2);
|
||||||
PIDisplay.renderer.glDrawLine(x + 1, y + 1, x + 1, y + marginBottom / 2);
|
DisplayManager.renderer.glDrawLine(x + 2, y + marginBottom / 2 + 1, x + 2, y + marginBottom - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 2, y + marginBottom / 2 + 1, x + 2, y + marginBottom - 1);
|
DisplayManager.renderer.glDrawLine(x + 0, y + marginBottom, x + 1, y + marginBottom);
|
||||||
PIDisplay.renderer.glDrawLine(x + 0, y + marginBottom, x + 1, y + marginBottom);
|
DisplayManager.renderer.glDrawLine(x + 2, y + marginBottom + 1, x + 2, y + marginBottom + spazioSopra / 2 - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 2, y + marginBottom + 1, x + 2, y + marginBottom + spazioSopra / 2 - 1);
|
DisplayManager.renderer.glDrawLine(x + 1, y + marginBottom + spazioSopra / 2, x + 1, y + h - 1);
|
||||||
PIDisplay.renderer.glDrawLine(x + 1, y + marginBottom + spazioSopra / 2, x + 1, y + h - 1);
|
DisplayManager.renderer.glDrawLine(x + 2, y + h, x + 3, y + h);
|
||||||
PIDisplay.renderer.glDrawLine(x + 2, y + h, x + 3, y + h);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -1,7 +1,5 @@
|
|||||||
package org.warp.picalculator.math.functions.equations;
|
package org.warp.picalculator.math.functions.equations;
|
||||||
|
|
||||||
import static org.warp.picalculator.gui.graphicengine.cpu.CPUDisplay.Render.glDrawLine;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
@ -39,7 +37,7 @@ public class EquationsSystemPart extends AnteriorFunction {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void draw(int x, int y) {
|
public void draw(int x, int y) {
|
||||||
final int h = this.getHeight() - 1;
|
final int h = getHeight() - 1;
|
||||||
final int paddingTop = 3;
|
final int paddingTop = 3;
|
||||||
final int spazioSotto = (h - 3 - 2) / 2 + paddingTop;
|
final int spazioSotto = (h - 3 - 2) / 2 + paddingTop;
|
||||||
final int spazioSopra = h - spazioSotto;
|
final int spazioSopra = h - spazioSotto;
|
||||||
@ -67,4 +65,22 @@ public class EquationsSystemPart extends AnteriorFunction {
|
|||||||
public int getLine() {
|
public int getLine() {
|
||||||
return line;
|
return line;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected ArrayList<Function> solve() throws Error {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected boolean isSolvable() {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean equals(Object o) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -35,14 +35,14 @@ public class Sine extends AnteriorFunction {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (root.angleMode == AngleMode.DEG) {
|
if (root.angleMode == AngleMode.DEG) {
|
||||||
Function[] solvableValues = new Function[]{new Number(root, 0), new Number(root, 30), new Number(root, 90), };
|
final Function[] solvableValues = new Function[] { new Number(root, 0), new Number(root, 30), new Number(root, 90), };
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ArrayList<Function> solve() throws Error {
|
public ArrayList<Function> solve() throws Error {
|
||||||
ArrayList<Function> results = new ArrayList<>();
|
final ArrayList<Function> results = new ArrayList<>();
|
||||||
if (variable instanceof Number) {
|
if (variable instanceof Number) {
|
||||||
if (root.exactMode == false) {
|
if (root.exactMode == false) {
|
||||||
results.add(new Number(root, BigDecimalMath.sin(((Number) variable).getTerm())));
|
results.add(new Number(root, BigDecimalMath.sin(((Number) variable).getTerm())));
|
||||||
@ -54,7 +54,7 @@ public class Sine extends AnteriorFunction {
|
|||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (o instanceof Sine) {
|
if (o instanceof Sine) {
|
||||||
AnteriorFunction f = (AnteriorFunction) o;
|
final AnteriorFunction f = (AnteriorFunction) o;
|
||||||
if (variable.equals(f.getVariable())) {
|
if (variable.equals(f.getVariable())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -16,6 +16,7 @@ import org.warp.picalculator.math.functions.SumSubtraction;
|
|||||||
* Expand rule<br>
|
* Expand rule<br>
|
||||||
* <b>-(+a+b) = -a-b</b><br>
|
* <b>-(+a+b) = -a-b</b><br>
|
||||||
* <b>-(+a-b) = -a+b</b>
|
* <b>-(+a-b) = -a+b</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@ -23,9 +24,9 @@ public class ExpandRule1 {
|
|||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
if (f instanceof Negative) {
|
if (f instanceof Negative) {
|
||||||
Negative fnc = (Negative) f;
|
final Negative fnc = (Negative) f;
|
||||||
if (fnc.getVariable() instanceof Expression) {
|
if (fnc.getVariable() instanceof Expression) {
|
||||||
Expression expr = (Expression) fnc.getVariable();
|
final Expression expr = (Expression) fnc.getVariable();
|
||||||
if (expr.getVariablesLength() == 1) {
|
if (expr.getVariablesLength() == 1) {
|
||||||
if (expr.getVariable(0) instanceof Sum) {
|
if (expr.getVariable(0) instanceof Sum) {
|
||||||
return true;
|
return true;
|
||||||
@ -37,9 +38,9 @@ public class ExpandRule1 {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (f instanceof Subtraction || f instanceof SumSubtraction) {
|
} else if (f instanceof Subtraction || f instanceof SumSubtraction) {
|
||||||
FunctionTwoValues fnc = (FunctionTwoValues) f;
|
final FunctionTwoValues fnc = (FunctionTwoValues) f;
|
||||||
if (fnc.getVariable2() instanceof Expression) {
|
if (fnc.getVariable2() instanceof Expression) {
|
||||||
Expression expr = (Expression) fnc.getVariable2();
|
final Expression expr = (Expression) fnc.getVariable2();
|
||||||
if (expr.getVariablesLength() == 1) {
|
if (expr.getVariablesLength() == 1) {
|
||||||
if (expr.getVariable(0) instanceof Sum) {
|
if (expr.getVariable(0) instanceof Sum) {
|
||||||
return true;
|
return true;
|
||||||
@ -55,16 +56,16 @@ public class ExpandRule1 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
|
|
||||||
Expression expr = null;
|
Expression expr = null;
|
||||||
int fromSubtraction = 0;
|
int fromSubtraction = 0;
|
||||||
FunctionTwoValues subtraction = null;
|
FunctionTwoValues subtraction = null;
|
||||||
if (f instanceof Negative) {
|
if (f instanceof Negative) {
|
||||||
expr = ((Expression)((Negative) f).getVariable());
|
expr = ((Expression) ((Negative) f).getVariable());
|
||||||
} else if (f instanceof Subtraction || f instanceof SumSubtraction) {
|
} else if (f instanceof Subtraction || f instanceof SumSubtraction) {
|
||||||
expr = ((Expression)((FunctionTwoValues) f).getVariable2());
|
expr = ((Expression) ((FunctionTwoValues) f).getVariable2());
|
||||||
if (f instanceof Subtraction) {
|
if (f instanceof Subtraction) {
|
||||||
fromSubtraction = 1;
|
fromSubtraction = 1;
|
||||||
} else {
|
} else {
|
||||||
@ -76,47 +77,47 @@ public class ExpandRule1 {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Function fnc = expr.getVariable(0);
|
final Function fnc = expr.getVariable(0);
|
||||||
if (fnc instanceof Sum) {
|
if (fnc instanceof Sum) {
|
||||||
Function a = ((Sum) fnc).getVariable1();
|
final Function a = ((Sum) fnc).getVariable1();
|
||||||
Function b = ((Sum) fnc).getVariable2();
|
final Function b = ((Sum) fnc).getVariable2();
|
||||||
Subtraction fnc2 = new Subtraction(root, null, b);
|
final Subtraction fnc2 = new Subtraction(root, null, b);
|
||||||
fnc2.setVariable1(new Negative(root, a));
|
fnc2.setVariable1(new Negative(root, a));
|
||||||
if (fromSubtraction > 0) {
|
if (fromSubtraction > 0) {
|
||||||
subtraction = new Subtraction(root, null, null);
|
subtraction = new Subtraction(root, null, null);
|
||||||
subtraction.setVariable1(((FunctionTwoValues)f).getVariable1());
|
subtraction.setVariable1(((FunctionTwoValues) f).getVariable1());
|
||||||
subtraction.setVariable2(fnc2);
|
subtraction.setVariable2(fnc2);
|
||||||
result.add(subtraction);
|
result.add(subtraction);
|
||||||
} else {
|
} else {
|
||||||
result.add(fnc2);
|
result.add(fnc2);
|
||||||
}
|
}
|
||||||
} else if (fnc instanceof Subtraction) {
|
} else if (fnc instanceof Subtraction) {
|
||||||
Function a = ((Subtraction) fnc).getVariable1();
|
final Function a = ((Subtraction) fnc).getVariable1();
|
||||||
Function b = ((Subtraction) fnc).getVariable2();
|
final Function b = ((Subtraction) fnc).getVariable2();
|
||||||
Sum fnc2 = new Sum(root, null, b);
|
final Sum fnc2 = new Sum(root, null, b);
|
||||||
fnc2.setVariable1(new Negative(root, a));
|
fnc2.setVariable1(new Negative(root, a));
|
||||||
if (fromSubtraction > 0) {
|
if (fromSubtraction > 0) {
|
||||||
subtraction = new Subtraction(root, null, null);
|
subtraction = new Subtraction(root, null, null);
|
||||||
subtraction.setVariable1(((FunctionTwoValues)f).getVariable1());
|
subtraction.setVariable1(((FunctionTwoValues) f).getVariable1());
|
||||||
subtraction.setVariable2(fnc2);
|
subtraction.setVariable2(fnc2);
|
||||||
result.add(subtraction);
|
result.add(subtraction);
|
||||||
} else {
|
} else {
|
||||||
result.add(fnc2);
|
result.add(fnc2);
|
||||||
}
|
}
|
||||||
} else if (fnc instanceof SumSubtraction) {
|
} else if (fnc instanceof SumSubtraction) {
|
||||||
Function a = ((SumSubtraction) fnc).getVariable1();
|
final Function a = ((SumSubtraction) fnc).getVariable1();
|
||||||
Function b = ((SumSubtraction) fnc).getVariable2();
|
final Function b = ((SumSubtraction) fnc).getVariable2();
|
||||||
Sum fnc2 = new Sum(root, null, b);
|
final Sum fnc2 = new Sum(root, null, b);
|
||||||
fnc2.setVariable1(new Negative(root, a));
|
fnc2.setVariable1(new Negative(root, a));
|
||||||
Subtraction fnc3 = new Subtraction(root, null, b);
|
final Subtraction fnc3 = new Subtraction(root, null, b);
|
||||||
fnc3.setVariable1(new Negative(root, a));
|
fnc3.setVariable1(new Negative(root, a));
|
||||||
if (fromSubtraction > 0) {
|
if (fromSubtraction > 0) {
|
||||||
subtraction = new SumSubtraction(root, null, null);
|
subtraction = new SumSubtraction(root, null, null);
|
||||||
subtraction.setVariable1(((FunctionTwoValues)f).getVariable1());
|
subtraction.setVariable1(((FunctionTwoValues) f).getVariable1());
|
||||||
subtraction.setVariable2(fnc2);
|
subtraction.setVariable2(fnc2);
|
||||||
result.add(subtraction);
|
result.add(subtraction);
|
||||||
subtraction = new SumSubtraction(root, null, null);
|
subtraction = new SumSubtraction(root, null, null);
|
||||||
subtraction.setVariable1(((FunctionTwoValues)f).getVariable1());
|
subtraction.setVariable1(((FunctionTwoValues) f).getVariable1());
|
||||||
subtraction.setVariable2(fnc3);
|
subtraction.setVariable2(fnc3);
|
||||||
result.add(subtraction);
|
result.add(subtraction);
|
||||||
result.add(subtraction);
|
result.add(subtraction);
|
||||||
|
@ -3,7 +3,6 @@ package org.warp.picalculator.math.rules;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
import org.warp.picalculator.Error;
|
import org.warp.picalculator.Error;
|
||||||
import org.warp.picalculator.math.Calculator;
|
|
||||||
import org.warp.picalculator.math.functions.Expression;
|
import org.warp.picalculator.math.functions.Expression;
|
||||||
import org.warp.picalculator.math.functions.Function;
|
import org.warp.picalculator.math.functions.Function;
|
||||||
import org.warp.picalculator.math.functions.Negative;
|
import org.warp.picalculator.math.functions.Negative;
|
||||||
@ -12,6 +11,7 @@ import org.warp.picalculator.math.functions.Subtraction;
|
|||||||
/**
|
/**
|
||||||
* Expand rule<br>
|
* Expand rule<br>
|
||||||
* <b>-(-a) = a</b>
|
* <b>-(-a) = a</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@ -19,15 +19,15 @@ public class ExpandRule5 {
|
|||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
if (f instanceof Negative) {
|
if (f instanceof Negative) {
|
||||||
Negative fnc = (Negative) f;
|
final Negative fnc = (Negative) f;
|
||||||
if (fnc.getVariable() instanceof Expression) {
|
if (fnc.getVariable() instanceof Expression) {
|
||||||
Expression e = (Expression)fnc.getVariable();
|
final Expression e = (Expression) fnc.getVariable();
|
||||||
return e.getVariablesLength() == 1 && e.getVariable(0) instanceof Negative;
|
return e.getVariablesLength() == 1 && e.getVariable(0) instanceof Negative;
|
||||||
}
|
}
|
||||||
} else if (f instanceof Subtraction) {
|
} else if (f instanceof Subtraction) {
|
||||||
Subtraction fnc = (Subtraction) f;
|
final Subtraction fnc = (Subtraction) f;
|
||||||
if (fnc.getVariable2() instanceof Expression) {
|
if (fnc.getVariable2() instanceof Expression) {
|
||||||
Expression e = (Expression)fnc.getVariable2();
|
final Expression e = (Expression) fnc.getVariable2();
|
||||||
return e.getVariablesLength() == 1 && e.getVariable(0) instanceof Negative;
|
return e.getVariablesLength() == 1 && e.getVariable(0) instanceof Negative;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -35,15 +35,15 @@ public class ExpandRule5 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Function a = null;
|
final Function a = null;
|
||||||
|
|
||||||
if (f instanceof Negative) {
|
if (f instanceof Negative) {
|
||||||
Negative fnc = (Negative) f;
|
final Negative fnc = (Negative) f;
|
||||||
result.add(((Negative)((Expression)fnc.getVariable()).getVariable(0)).getVariable());
|
result.add(((Negative) ((Expression) fnc.getVariable()).getVariable(0)).getVariable());
|
||||||
} else if (f instanceof Subtraction) {
|
} else if (f instanceof Subtraction) {
|
||||||
Subtraction fnc = (Subtraction) f;
|
final Subtraction fnc = (Subtraction) f;
|
||||||
result.add(((Negative)((Expression)fnc.getVariable2()).getVariable(0)).getVariable());
|
result.add(((Negative) ((Expression) fnc.getVariable2()).getVariable(0)).getVariable());
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -11,14 +11,15 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Exponent rule<br>
|
* Exponent rule<br>
|
||||||
* <b>1^a=1</b>
|
* <b>1^a=1</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class ExponentRule1 {
|
public class ExponentRule1 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
if (fnc.getVariable1().equals(new Number(root, 1))) {
|
if (fnc.getVariable1().equals(new Number(root, 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -26,8 +27,8 @@ public class ExponentRule1 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
result.add(new Number(root, 1));
|
result.add(new Number(root, 1));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -13,13 +13,14 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Exponent rule<br>
|
* Exponent rule<br>
|
||||||
* <b>a*a=a^2</b>
|
* <b>a*a=a^2</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class ExponentRule15 {
|
public class ExponentRule15 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Multiplication fnc = (Multiplication) f;
|
final Multiplication fnc = (Multiplication) f;
|
||||||
if (fnc.getVariable1().equals(fnc.getVariable2())) {
|
if (fnc.getVariable1().equals(fnc.getVariable2())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -27,14 +28,14 @@ public class ExponentRule15 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Multiplication fnc = (Multiplication) f;
|
final Multiplication fnc = (Multiplication) f;
|
||||||
Power p = new Power(root, null, null);
|
final Power p = new Power(root, null, null);
|
||||||
Expression expr = new Expression(root);
|
final Expression expr = new Expression(root);
|
||||||
Function a = fnc.getVariable1();
|
final Function a = fnc.getVariable1();
|
||||||
expr.addFunctionToEnd(a);
|
expr.addFunctionToEnd(a);
|
||||||
Number two = new Number(root, 2);
|
final Number two = new Number(root, 2);
|
||||||
p.setVariable1(expr);
|
p.setVariable1(expr);
|
||||||
p.setVariable2(two);
|
p.setVariable2(two);
|
||||||
result.add(p);
|
result.add(p);
|
||||||
|
@ -14,6 +14,7 @@ import org.warp.picalculator.math.functions.Root;
|
|||||||
/**
|
/**
|
||||||
* Exponent rule<br>
|
* Exponent rule<br>
|
||||||
* <b>a√x=x^1/a</b>
|
* <b>a√x=x^1/a</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@ -21,7 +22,7 @@ public class ExponentRule16 {
|
|||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
if (f instanceof Root) {
|
if (f instanceof Root) {
|
||||||
Root fnc = (Root) f;
|
final Root fnc = (Root) f;
|
||||||
if (fnc.getVariable1().equals(fnc.getVariable2())) {
|
if (fnc.getVariable1().equals(fnc.getVariable2())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -30,14 +31,14 @@ public class ExponentRule16 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Multiplication fnc = (Multiplication) f;
|
final Multiplication fnc = (Multiplication) f;
|
||||||
Power p = new Power(fnc.getRoot(), null, null);
|
final Power p = new Power(fnc.getRoot(), null, null);
|
||||||
Expression expr = new Expression(root);
|
final Expression expr = new Expression(root);
|
||||||
Function a = fnc.getVariable1();
|
final Function a = fnc.getVariable1();
|
||||||
expr.addFunctionToEnd(a);
|
expr.addFunctionToEnd(a);
|
||||||
Number two = new Number(root, 2);
|
final Number two = new Number(root, 2);
|
||||||
p.setVariable1(expr);
|
p.setVariable1(expr);
|
||||||
p.setVariable2(two);
|
p.setVariable2(two);
|
||||||
result.add(p);
|
result.add(p);
|
||||||
|
@ -10,13 +10,14 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Exponent rule<br>
|
* Exponent rule<br>
|
||||||
* <b>a^1=a</b>
|
* <b>a^1=a</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class ExponentRule2 {
|
public class ExponentRule2 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
if (fnc.getVariable2().equals(new Number(f.getRoot(), 1))) {
|
if (fnc.getVariable2().equals(new Number(f.getRoot(), 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -24,8 +25,8 @@ public class ExponentRule2 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
result.add(((Power)f).getVariable1());
|
result.add(((Power) f).getVariable1());
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -10,13 +10,14 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Exponent rule<br>
|
* Exponent rule<br>
|
||||||
* <b>a^0=1</b>
|
* <b>a^0=1</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class ExponentRule3 {
|
public class ExponentRule3 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
if (fnc.getVariable2().equals(new Number(f.getRoot(), 0))) {
|
if (fnc.getVariable2().equals(new Number(f.getRoot(), 0))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -24,7 +25,7 @@ public class ExponentRule3 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
result.add(new Number(f.getRoot(), 1));
|
result.add(new Number(f.getRoot(), 1));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -13,13 +13,14 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Exponent rule<br>
|
* Exponent rule<br>
|
||||||
* <b>(a*b)^n=a^n*b^n</b>
|
* <b>(a*b)^n=a^n*b^n</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class ExponentRule4 {
|
public class ExponentRule4 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
if (fnc.getVariable1() instanceof Expression && ((Expression) fnc.getVariable1()).getVariablesLength() == 1 && ((Expression) fnc.getVariable1()).getVariable(0) instanceof Multiplication && fnc.getVariable2() instanceof Number) {
|
if (fnc.getVariable1() instanceof Expression && ((Expression) fnc.getVariable1()).getVariablesLength() == 1 && ((Expression) fnc.getVariable1()).getVariable(0) instanceof Multiplication && fnc.getVariable2() instanceof Number) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -27,22 +28,22 @@ public class ExponentRule4 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
Expression expr = (Expression) fnc.getVariable1();
|
final Expression expr = (Expression) fnc.getVariable1();
|
||||||
Multiplication mult = (Multiplication) expr.getVariable(0);
|
final Multiplication mult = (Multiplication) expr.getVariable(0);
|
||||||
Function a = mult.getVariable1();
|
final Function a = mult.getVariable1();
|
||||||
Function b = mult.getVariable2();
|
final Function b = mult.getVariable2();
|
||||||
Number n = (Number) fnc.getVariable2();
|
final Number n = (Number) fnc.getVariable2();
|
||||||
Multiplication retMult = new Multiplication(root, null, null);
|
final Multiplication retMult = new Multiplication(root, null, null);
|
||||||
Power p1 = new Power(root, null, null);
|
final Power p1 = new Power(root, null, null);
|
||||||
Expression e1 = new Expression(root);
|
final Expression e1 = new Expression(root);
|
||||||
e1.addFunctionToEnd(a);
|
e1.addFunctionToEnd(a);
|
||||||
p1.setVariable1(e1);
|
p1.setVariable1(e1);
|
||||||
p1.setVariable2(n);
|
p1.setVariable2(n);
|
||||||
Power p2 = new Power(root, null, null);
|
final Power p2 = new Power(root, null, null);
|
||||||
Expression e2 = new Expression(root);
|
final Expression e2 = new Expression(root);
|
||||||
e2.addFunctionToEnd(b);
|
e2.addFunctionToEnd(b);
|
||||||
p2.setVariable1(e2);
|
p2.setVariable1(e2);
|
||||||
p2.setVariable2(n);
|
p2.setVariable2(n);
|
||||||
|
@ -11,19 +11,20 @@ import org.warp.picalculator.math.functions.Number;
|
|||||||
/**
|
/**
|
||||||
* Fractions rule<br>
|
* Fractions rule<br>
|
||||||
* <b>0 / a = 0</b>
|
* <b>0 / a = 0</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class FractionsRule1 {
|
public class FractionsRule1 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
Division fnc = (Division) f;
|
final Division fnc = (Division) f;
|
||||||
if (fnc.getVariable1() instanceof Number) {
|
if (fnc.getVariable1() instanceof Number) {
|
||||||
Number numb1 = (Number) fnc.getVariable1();
|
final Number numb1 = (Number) fnc.getVariable1();
|
||||||
if (numb1.equals(new Number(root, 0))) {
|
if (numb1.equals(new Number(root, 0))) {
|
||||||
if (fnc.getVariable2() instanceof Number) {
|
if (fnc.getVariable2() instanceof Number) {
|
||||||
Number numb2 = (Number) fnc.getVariable2();
|
final Number numb2 = (Number) fnc.getVariable2();
|
||||||
if (numb2.equals(new Number(root, 0))) {
|
if (numb2.equals(new Number(root, 0))) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -35,7 +36,7 @@ public class FractionsRule1 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
result.add(new Number(f.getRoot(), 0));
|
result.add(new Number(f.getRoot(), 0));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -10,15 +10,16 @@ import org.warp.picalculator.math.functions.Number;
|
|||||||
/**
|
/**
|
||||||
* Fractions rule<br>
|
* Fractions rule<br>
|
||||||
* <b>a / 1 = a</b>
|
* <b>a / 1 = a</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class FractionsRule2 {
|
public class FractionsRule2 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Division fnc = (Division) f;
|
final Division fnc = (Division) f;
|
||||||
if (fnc.getVariable2() instanceof Number) {
|
if (fnc.getVariable2() instanceof Number) {
|
||||||
Number numb = (Number) fnc.getVariable2();
|
final Number numb = (Number) fnc.getVariable2();
|
||||||
if (numb.equals(new Number(f.getRoot(), 1))) {
|
if (numb.equals(new Number(f.getRoot(), 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -27,8 +28,8 @@ public class FractionsRule2 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Division fnc = (Division) f;
|
final Division fnc = (Division) f;
|
||||||
result.add(fnc.getVariable1());
|
result.add(fnc.getVariable1());
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -10,13 +10,14 @@ import org.warp.picalculator.math.functions.Number;
|
|||||||
/**
|
/**
|
||||||
* Fractions rule<br>
|
* Fractions rule<br>
|
||||||
* <b>a / a = 1</b>
|
* <b>a / a = 1</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class FractionsRule3 {
|
public class FractionsRule3 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Division fnc = (Division) f;
|
final Division fnc = (Division) f;
|
||||||
if (fnc.getVariable1().equals(fnc.getVariable2())) {
|
if (fnc.getVariable1().equals(fnc.getVariable2())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -24,7 +25,7 @@ public class FractionsRule3 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
result.add(new Number(f.getRoot(), 1));
|
result.add(new Number(f.getRoot(), 1));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -11,15 +11,16 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Fractions rule<br>
|
* Fractions rule<br>
|
||||||
* <b>(a / b) ^ -1 = b / a</b>
|
* <b>(a / b) ^ -1 = b / a</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class FractionsRule4 {
|
public class FractionsRule4 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
if (fnc.getVariable1() instanceof Division && fnc.getVariable2() instanceof Number) {
|
if (fnc.getVariable1() instanceof Division && fnc.getVariable2() instanceof Number) {
|
||||||
Number n2 = (Number) fnc.getVariable2();
|
final Number n2 = (Number) fnc.getVariable2();
|
||||||
if (n2.equals(new Number(f.getRoot(), -1))) {
|
if (n2.equals(new Number(f.getRoot(), -1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -28,11 +29,11 @@ public class FractionsRule4 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
Function a = ((Division)fnc.getVariable1()).getVariable1();
|
final Function a = ((Division) fnc.getVariable1()).getVariable1();
|
||||||
Function b = ((Division)fnc.getVariable1()).getVariable2();
|
final Function b = ((Division) fnc.getVariable1()).getVariable2();
|
||||||
Division res = new Division(f.getRoot(), b, a);
|
final Division res = new Division(f.getRoot(), b, a);
|
||||||
result.add(res);
|
result.add(res);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
package org.warp.picalculator.math.rules;
|
package org.warp.picalculator.math.rules;
|
||||||
|
|
||||||
import java.math.BigDecimal;
|
import java.math.BigDecimal;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
@ -12,15 +13,16 @@ import org.warp.picalculator.math.functions.Power;
|
|||||||
/**
|
/**
|
||||||
* Fractions rule<br>
|
* Fractions rule<br>
|
||||||
* <b>(a / b) ^ -c = (b / a) ^ c</b>
|
* <b>(a / b) ^ -c = (b / a) ^ c</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class FractionsRule5 {
|
public class FractionsRule5 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
if (fnc.getVariable1() instanceof Division && fnc.getVariable2() instanceof Number) {
|
if (fnc.getVariable1() instanceof Division && fnc.getVariable2() instanceof Number) {
|
||||||
Number n2 = (Number) fnc.getVariable2();
|
final Number n2 = (Number) fnc.getVariable2();
|
||||||
if (n2.getTerm().compareTo(BigDecimal.ZERO) < 0) {
|
if (n2.getTerm().compareTo(BigDecimal.ZERO) < 0) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -29,14 +31,14 @@ public class FractionsRule5 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Power fnc = (Power) f;
|
final Power fnc = (Power) f;
|
||||||
Function a = ((Division)fnc.getVariable1()).getVariable1();
|
final Function a = ((Division) fnc.getVariable1()).getVariable1();
|
||||||
Function b = ((Division)fnc.getVariable1()).getVariable2();
|
final Function b = ((Division) fnc.getVariable1()).getVariable2();
|
||||||
Function c = ((Number)fnc.getVariable2()).multiply(new Number(root, "-1"));
|
final Function c = ((Number) fnc.getVariable2()).multiply(new Number(root, "-1"));
|
||||||
Division dv = new Division(root, b, a);
|
final Division dv = new Division(root, b, a);
|
||||||
Power pow = new Power(root, dv, c);
|
final Power pow = new Power(root, dv, c);
|
||||||
result.add(pow);
|
result.add(pow);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -11,22 +11,23 @@ import org.warp.picalculator.math.functions.Number;
|
|||||||
/**
|
/**
|
||||||
* Number rule<br>
|
* Number rule<br>
|
||||||
* <b>a * 0 = 0</b>
|
* <b>a * 0 = 0</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class NumberRule1 {
|
public class NumberRule1 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
Multiplication mult = (Multiplication) f;
|
final Multiplication mult = (Multiplication) f;
|
||||||
if (mult.getVariable1() instanceof Number) {
|
if (mult.getVariable1() instanceof Number) {
|
||||||
Number numb = (Number) mult.getVariable1();
|
final Number numb = (Number) mult.getVariable1();
|
||||||
if (numb.equals(new Number(root, 0))) {
|
if (numb.equals(new Number(root, 0))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (mult.getVariable2() instanceof Number) {
|
if (mult.getVariable2() instanceof Number) {
|
||||||
Number numb = (Number) mult.getVariable2();
|
final Number numb = (Number) mult.getVariable2();
|
||||||
if (numb.equals(new Number(root, 0))) {
|
if (numb.equals(new Number(root, 0))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -35,7 +36,7 @@ public class NumberRule1 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
result.add(new Number(f.getRoot(), "0"));
|
result.add(new Number(f.getRoot(), "0"));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -11,22 +11,23 @@ import org.warp.picalculator.math.functions.Number;
|
|||||||
/**
|
/**
|
||||||
* Number rule<br>
|
* Number rule<br>
|
||||||
* <b>a * 1 = a</b>
|
* <b>a * 1 = a</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public class NumberRule2 {
|
public class NumberRule2 {
|
||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
Multiplication mult = (Multiplication) f;
|
final Multiplication mult = (Multiplication) f;
|
||||||
if (mult.getVariable1() instanceof Number) {
|
if (mult.getVariable1() instanceof Number) {
|
||||||
Number numb = (Number) mult.getVariable1();
|
final Number numb = (Number) mult.getVariable1();
|
||||||
if (numb.equals(new Number(root, 1))) {
|
if (numb.equals(new Number(root, 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (mult.getVariable2() instanceof Number) {
|
if (mult.getVariable2() instanceof Number) {
|
||||||
Number numb = (Number) mult.getVariable2();
|
final Number numb = (Number) mult.getVariable2();
|
||||||
if (numb.equals(new Number(root, 1))) {
|
if (numb.equals(new Number(root, 1))) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -35,20 +36,20 @@ public class NumberRule2 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
Function a = null;
|
Function a = null;
|
||||||
boolean aFound = false;
|
boolean aFound = false;
|
||||||
Multiplication mult = (Multiplication) f;
|
final Multiplication mult = (Multiplication) f;
|
||||||
if (aFound == false & mult.getVariable1() instanceof Number) {
|
if (aFound == false & mult.getVariable1() instanceof Number) {
|
||||||
Number numb = (Number) mult.getVariable1();
|
final Number numb = (Number) mult.getVariable1();
|
||||||
if (numb.equals(new Number(root, 1))) {
|
if (numb.equals(new Number(root, 1))) {
|
||||||
a = mult.getVariable2();
|
a = mult.getVariable2();
|
||||||
aFound = true;
|
aFound = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (aFound == false && mult.getVariable2() instanceof Number) {
|
if (aFound == false && mult.getVariable2() instanceof Number) {
|
||||||
Number numb = (Number) mult.getVariable2();
|
final Number numb = (Number) mult.getVariable2();
|
||||||
if (numb.equals(new Number(root, 1))) {
|
if (numb.equals(new Number(root, 1))) {
|
||||||
a = mult.getVariable1();
|
a = mult.getVariable1();
|
||||||
aFound = true;
|
aFound = true;
|
||||||
|
@ -17,6 +17,7 @@ import org.warp.picalculator.math.functions.SumSubtraction;
|
|||||||
* <b>a - a = 0</b><br>
|
* <b>a - a = 0</b><br>
|
||||||
* <b>-a + a = 0</b><br>
|
* <b>-a + a = 0</b><br>
|
||||||
* <b>a ± a = {0, 2a}</b>
|
* <b>a ± a = {0, 2a}</b>
|
||||||
|
*
|
||||||
* @author Andrea Cavalli
|
* @author Andrea Cavalli
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@ -24,20 +25,20 @@ public class NumberRule3 {
|
|||||||
|
|
||||||
public static boolean compare(Function f) {
|
public static boolean compare(Function f) {
|
||||||
if (f instanceof Subtraction) {
|
if (f instanceof Subtraction) {
|
||||||
Subtraction sub = (Subtraction) f;
|
final Subtraction sub = (Subtraction) f;
|
||||||
if (sub.getVariable1().equals(sub.getVariable2())) {
|
if (sub.getVariable1().equals(sub.getVariable2())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
} else if (f instanceof Sum) {
|
} else if (f instanceof Sum) {
|
||||||
Sum sub = (Sum) f;
|
final Sum sub = (Sum) f;
|
||||||
if (sub.getVariable1() instanceof Negative) {
|
if (sub.getVariable1() instanceof Negative) {
|
||||||
Negative neg = (Negative) sub.getVariable1();
|
final Negative neg = (Negative) sub.getVariable1();
|
||||||
if (neg.getVariable().equals(sub.getVariable2())) {
|
if (neg.getVariable().equals(sub.getVariable2())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (f instanceof SumSubtraction) {
|
} else if (f instanceof SumSubtraction) {
|
||||||
SumSubtraction sub = (SumSubtraction) f;
|
final SumSubtraction sub = (SumSubtraction) f;
|
||||||
if (sub.getVariable1().equals(sub.getVariable2())) {
|
if (sub.getVariable1().equals(sub.getVariable2())) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -46,10 +47,10 @@ public class NumberRule3 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static ArrayList<Function> execute(Function f) throws Error {
|
public static ArrayList<Function> execute(Function f) throws Error {
|
||||||
Calculator root = f.getRoot();
|
final Calculator root = f.getRoot();
|
||||||
ArrayList<Function> result = new ArrayList<>();
|
final ArrayList<Function> result = new ArrayList<>();
|
||||||
if (f instanceof SumSubtraction) {
|
if (f instanceof SumSubtraction) {
|
||||||
Multiplication mul = new Multiplication(root, null, null);
|
final Multiplication mul = new Multiplication(root, null, null);
|
||||||
mul.setVariable1(new Number(root, 2));
|
mul.setVariable1(new Number(root, 2));
|
||||||
mul.setVariable2(f);
|
mul.setVariable2(f);
|
||||||
result.add(mul);
|
result.add(mul);
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user