123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387
  1. import java.util.Scanner;
  2. /**
  3. * Created by leon on 2/9/18.
  4. *
  5. * Expanded by Allison & Alfredo on 5/25/2018
  6. *
  7. * The Console displays messages and fetches calculations for the user
  8. * while they are using the calculator. It uses the Calculator class to
  9. * make calculations, and the NumericInputParser to correctly read user
  10. * input and format calculations
  11. *
  12. */
  13. public class Console {
  14. private Calculator calc;
  15. private NumericInputParser parse;
  16. public Console(){
  17. calc = new Calculator();
  18. parse = new NumericInputParser();
  19. }
  20. public void runCommandLoop()
  21. {
  22. Scanner input = new Scanner(System.in);
  23. println("Welcome to this calculator!");
  24. println("For a user guide, enter '?'");
  25. while (true) {
  26. print("Enter a command: ");
  27. String command = input.nextLine();
  28. if (command.equalsIgnoreCase("exit")) {
  29. print("Thanks for calculating with us!");
  30. break;
  31. }
  32. else if (command.equalsIgnoreCase("clear")){
  33. calc.clear();
  34. printResult();
  35. }
  36. else if (command.equalsIgnoreCase("val") ||
  37. command.equalsIgnoreCase("=")){
  38. printResult();
  39. }
  40. else if (command.equalsIgnoreCase("set")) {
  41. calc.setDisplayValue(getDoubleInput("Enter new value: "));
  42. printResult();
  43. }
  44. else if (command.equalsIgnoreCase("?")){
  45. printGuide();
  46. }
  47. //Core Features
  48. else if (command.equalsIgnoreCase("add") ||
  49. command.equalsIgnoreCase("+")) {
  50. printValue();
  51. Double d = getDoubleInput(" + ");
  52. if (d != null) {
  53. calc.add(d);
  54. printResult();
  55. }
  56. }
  57. else if (command.equalsIgnoreCase("sub") ||
  58. command.equalsIgnoreCase("-")) {
  59. printValue();
  60. Double d = getDoubleInput(" - ");
  61. if (d != null) {
  62. calc.subtract(d);
  63. printResult();
  64. }
  65. }
  66. else if (command.equalsIgnoreCase("mult") ||
  67. command.equalsIgnoreCase("*")) {
  68. printValue();
  69. Double d = getDoubleInput(" * ");
  70. if (d != null) {
  71. calc.multiply(d);
  72. printResult();
  73. }
  74. }
  75. else if (command.equalsIgnoreCase("div") ||
  76. command.equalsIgnoreCase("/")) {
  77. printValue();
  78. Double d = getDoubleInput(" / ");
  79. if (d != null) {
  80. calc.divide(d);
  81. printResult();
  82. }
  83. }
  84. else if (command.equalsIgnoreCase("sq")) {
  85. println(getValue() + "^2");
  86. calc.square();
  87. printResult();
  88. }
  89. else if (command.equalsIgnoreCase("pow") ||
  90. command.equalsIgnoreCase("^")) {
  91. printValue();
  92. calc.pow(getDoubleInput("^ "));
  93. printResult();
  94. }
  95. else if (command.equalsIgnoreCase("sqrt")) {
  96. println("\u221A" + getValue()); // unicode is for radical symbol
  97. calc.squareRoot();
  98. printResult();
  99. }
  100. else if (command.equalsIgnoreCase("inv")) {
  101. println("1\\" + getValue());
  102. calc.inverse();
  103. printResult();
  104. }
  105. else if (command.equalsIgnoreCase("chngsign")) {
  106. calc.changeSign();
  107. printResult();
  108. }
  109. //trig functions
  110. else if (command.equalsIgnoreCase("sin")) {
  111. Double d = getAngleInput("sin() ");
  112. if (d != null) {
  113. calc.sin(d);
  114. printResult();
  115. }
  116. }
  117. else if (command.equalsIgnoreCase("cos")) {
  118. Double d = getAngleInput("cos() ");
  119. if (d != null) {
  120. calc.cos(d);
  121. printResult();
  122. }
  123. }
  124. else if (command.equalsIgnoreCase("tan")) {
  125. Double d = getAngleInput("tan() ");
  126. if (d != null) {
  127. calc.tan(d);
  128. printResult();
  129. }
  130. }
  131. else if (command.equalsIgnoreCase("cot")) {
  132. Double d = getDoubleInput("cot() ");
  133. if (d != null) {
  134. calc.inverseTan(d);
  135. printTrigResult();
  136. }
  137. }
  138. else if (command.equalsIgnoreCase("csc")){
  139. Double d = getDoubleInput("csc() ");
  140. if (d != null) {
  141. calc.inverseSin(d);
  142. printTrigResult();
  143. }
  144. }
  145. else if (command.equalsIgnoreCase("sec")){
  146. Double d = getDoubleInput("sec() ");
  147. if (d != null) {
  148. calc.inverseCos(d);
  149. printTrigResult();
  150. }
  151. }
  152. //Bonus Functions
  153. else if (command.equalsIgnoreCase("log")){
  154. println("log " + getValue());
  155. calc.log();
  156. printResult();
  157. }
  158. else if (command.equalsIgnoreCase("ln")){
  159. println("ln ", getValue());
  160. calc.naturalLog();
  161. printResult();
  162. }
  163. else if (command.equalsIgnoreCase("antilog")){
  164. println("antilog " + getValue());
  165. calc.inverseLog();
  166. printResult();
  167. }
  168. else if (command.equalsIgnoreCase("antiln")){
  169. print("antiln " + getValue());
  170. calc.inverseLn();
  171. printResult();
  172. }
  173. //Custom functions
  174. else if (command.equalsIgnoreCase("pi")){
  175. calc.displayPi();
  176. printResult();
  177. }
  178. else if (command.equalsIgnoreCase("e")){
  179. calc.displayE();
  180. printResult();
  181. }
  182. else if (command.equalsIgnoreCase("fact") ||
  183. command.equalsIgnoreCase("!")){
  184. calc.factorial();
  185. printResult();
  186. }
  187. //display mode changes
  188. else if (command.equalsIgnoreCase("hex") ||
  189. command.equalsIgnoreCase("oct") ||
  190. command.equalsIgnoreCase("dec") ||
  191. command.equalsIgnoreCase("bin") ){
  192. parse.switchDisplayMode(command);
  193. println("Display mode changed to %s", parse.getDisplayMode());
  194. }
  195. else if (command.equalsIgnoreCase("mode?")) {
  196. println("Current display mode is %s", parse.getDisplayMode());
  197. }
  198. else if (command.equalsIgnoreCase("mode")) {
  199. parse.switchDisplayMode();
  200. println("Display mode changed to %s", parse.getDisplayMode());
  201. }
  202. //trig units mode changes
  203. else if (command.equalsIgnoreCase("rad") ||
  204. command.equalsIgnoreCase("deg")) {
  205. parse.switchUnitsMode(command);
  206. println("Trig units changed to %s", parse.getTrigUnitsMode());
  207. }
  208. else if (command.equalsIgnoreCase("trig")) {
  209. parse.switchUnitsMode();
  210. println("Trig units changed to %s", parse.getTrigUnitsMode());
  211. }
  212. else if (command.equalsIgnoreCase("trig?")) {
  213. println("Current trig units: %s", parse.getTrigUnitsMode());
  214. }
  215. //memory features
  216. else if (command.equalsIgnoreCase("M+")) {
  217. calc.memSet();
  218. printMemory();
  219. }
  220. else if (command.equalsIgnoreCase("MC")) {
  221. calc.memClear();
  222. printMemory();
  223. }
  224. else if (command.equalsIgnoreCase("MRC")) {
  225. calc.mrc();
  226. printResult();
  227. }
  228. else {
  229. System.out.println("Invalid input. Enter '?' for a user guide");
  230. System.out.println("Enter 'exit' to quit");
  231. }
  232. }
  233. }
  234. public static void print(String output, Object... args) {
  235. System.out.printf(output, args);
  236. }
  237. public static void println(String output, Object... args) {
  238. print(output + "\n", args);
  239. }
  240. public void printResult() {
  241. if (!errCheck()) {
  242. println("= %s", parse.getFormattedNumber(calc.getDisplayValue()));
  243. }
  244. else {
  245. errMessage();
  246. }
  247. }
  248. private boolean errCheck(){
  249. boolean err = false;
  250. if (Double.isInfinite(calc.getDisplayValue())){
  251. err = true;
  252. }
  253. else if (Double.isNaN(calc.getDisplayValue())){
  254. err = true;
  255. }
  256. return err;
  257. }
  258. private void errMessage(){
  259. while(true){
  260. String clear = getStringInput("ERR ");
  261. if (clear.equalsIgnoreCase("clear")){
  262. calc.clear();
  263. calc.memClear();
  264. break;
  265. }
  266. }
  267. }
  268. public void printTrigResult() {
  269. if (!errCheck()) {
  270. println("= %s", parse.getFormattedAngle(calc.getDisplayValue()));
  271. }
  272. else {
  273. errMessage();
  274. }
  275. }
  276. public void printMemory() {
  277. println("mem = %s", parse.getFormattedNumber(calc.getMem()));
  278. }
  279. public void printValue() {
  280. print(parse.getFormattedNumber(calc.getDisplayValue()));
  281. }
  282. public String getValue() {
  283. return parse.getFormattedNumber(calc.getDisplayValue());
  284. }
  285. public String getStringInput(String prompt) {
  286. Scanner s = new Scanner(System.in);
  287. print(prompt);
  288. return s.nextLine();
  289. }
  290. public Double getDoubleInput(String prompt) {
  291. Scanner s = new Scanner(System.in);
  292. print(prompt);
  293. Double d = null;
  294. try {
  295. d = parse.getDouble(s.nextLine());
  296. }
  297. catch (NumberFormatException e) {
  298. errMessage();
  299. }
  300. return d;
  301. }
  302. public double getAngleInput(String prompt) {
  303. Scanner s = new Scanner(System.in);
  304. print(prompt);
  305. Double d = null;
  306. try {
  307. d = parse.getAngle(s.nextLine());
  308. }
  309. catch (NumberFormatException e) {
  310. errMessage();
  311. }
  312. return d;
  313. }
  314. public void printGuide(){
  315. println("Guide Under Construction");
  316. println("%-10s | %s", "Command: ", "Function: ");
  317. println("%-10s | %s", "?", "Prints the user manual to the screen");
  318. println("%-10s | %s", "exit", "Closes the calculator");
  319. println("%-10s | %s", "set", "Prompts the user to input a number to set to the display");
  320. println("%-10s | %s", "val or =", "Print the current value to the display");
  321. println("%-10s | %s", "add or +", "Adds an input value to the current value");
  322. println("%-10s | %s", "sub or -", "Subtracts an input value from the current value");
  323. println("%-10s | %s", "mult or *", "Multiplies the current value by an input value");
  324. println("%-10s | %s", "div or /", "Divides the current value by an input value");
  325. println("%-10s | %s", "sq", "Squares the current value");
  326. println("%-10s | %s", "pow or ^", "Raises the current value to an input power");
  327. println("%-10s | %s", "inv", "Calculates the inverse of the current value");
  328. println("%-10s | %s", "chngsign", "Changes the sign of the current value");
  329. println("%-10s | %s", "sin", "Calculates the sine of an input angle (Decimal mode reccommended)");
  330. println("%-10s | %s", "cos", "Calculates the cosine of an input angle (Decimal mode reccommended)");
  331. println("%-10s | %s", "tan", "Calculates the tangent of an input angle (Decimal mode reccommended)");
  332. println("%-10s | %s", "cot", "Calculates of the cotangent (inverse tangent) of an input angle (Decimal mode reccommended)");
  333. println("%-10s | %s", "csc", "Calculates the cosecant (inverse sine) of an input angle (Decimal mode reccommended)");
  334. println("%-10s | %s", "sec", "Calculates the secant (inverse cosine) of an input angle (Decimal mode reccommended)");
  335. println("%-10s | %s", "log", "Calculates the logarithm (base 10) of the current value");
  336. println("%-10s | %s", "ln", "Calculates the natural logarithm of the current value");
  337. println("%-10s | %s", "antilog", "Calculates the inverse logarithm of the current value");
  338. println("%-10s | %s", "antiln", "Calculates the inverse natural logarithm of the current value");
  339. println("%-10s | %s", "fact or !", "Calculates the factorial of the current value. If value is not an integer, it is truncated before caluclation");
  340. println("%-10s | %s", "pi", "Sets the current value to pi");
  341. println("%-10s | %s", "e", "Sets the current values to e");
  342. println("%-10s | %s", "hex", "Sets the display mode to hexadecimal. Affects both input and output values.");
  343. println("%-10s | %s", "oct", "Sets the display mode to octal. Affects both input and output values.");
  344. println("%-10s | %s", "bin", "Sets the display mode to binary. Affects both input and output values.");
  345. println("%-10s | %s", "dec", "Sets the display mode to decimal. Affects both input and output values (Reccommended setting for trig functions)");
  346. println("%-10s | %s", "mode", "Cyles through display modes. Affects both input and ouput values");
  347. println("%-10s | %s", "mode?", "Prints the current display mode");
  348. println("%-10s | %s", "rad", "Sets the trig units mode to radians");
  349. println("%-10s | %s", "deg", "Sets the trig units mode to degrees");
  350. println("%-10s | %s", "trig", "Toggles the trig units mode");
  351. println("%-10s | %s", "trig?", "Prints the current trig units mode");
  352. println("%-10s | %s", "M+", "Sets the memory value to the current value");
  353. println("%-10s | %s", "MC", "Clears the memory value");
  354. println("%-10s | %s", "MRC", "Sets the current value to the memory value");
  355. }
  356. }