diff options
-rw-r--r-- | actions.c | 98 | ||||
-rw-r--r-- | app-defaults/XCalc | 200 | ||||
-rw-r--r-- | math.c | 185 | ||||
-rw-r--r-- | xcalc.c | 19 | ||||
-rw-r--r-- | xcalc.h | 19 |
5 files changed, 426 insertions, 95 deletions
@@ -46,7 +46,9 @@ from the X Consortium. #endif static void add(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void and(Widget w, XEvent *ev, String *vector, Cardinal *count); static void back(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void base(Widget w, XEvent *ev, String *vector, Cardinal *count); static void bell(Widget w, XEvent *ev, String *vector, Cardinal *count); static void clearit(Widget w, XEvent *ev, String *vector, Cardinal *count); static void cosine(Widget w, XEvent *ev, String *vector, Cardinal *count); @@ -63,11 +65,14 @@ static void factorial(Widget w, XEvent *ev, String *vector, Cardinal *count); static void inverse(Widget w, XEvent *ev, String *vector, Cardinal *count); static void leftParen(Widget w, XEvent *ev, String *vector, Cardinal *count); static void logarithm(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void mod(Widget w, XEvent *ev, String *vector, Cardinal *count); static void multiply(Widget w, XEvent *ev, String *vector, Cardinal *count); static void naturalLog(Widget w, XEvent *ev, String *vector, Cardinal *count); static void negate(Widget w, XEvent *ev, String *vector, Cardinal *count); static void nop(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void not(Widget w, XEvent *ev, String *vector, Cardinal *count); static void off(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void or(Widget w, XEvent *ev, String *vector, Cardinal *count); static void pi(Widget w, XEvent *ev, String *vector, Cardinal *count); static void power(Widget w, XEvent *ev, String *vector, Cardinal *count); static void quit(Widget w, XEvent *ev, String *vector, Cardinal *count); @@ -77,6 +82,8 @@ static void rightParen(Widget w, XEvent *ev, String *vector, Cardinal *count); static void roll(Widget w, XEvent *ev, String *vector, Cardinal *count); static void scientific(Widget w, XEvent *ev, String *vector, Cardinal *count); static void selection(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void shl(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void shr(Widget w, XEvent *ev, String *vector, Cardinal *count); static void sine(Widget w, XEvent *ev, String *vector, Cardinal *count); static void square(Widget w, XEvent *ev, String *vector, Cardinal *count); static void squareRoot(Widget w, XEvent *ev, String *vector, Cardinal *count); @@ -85,6 +92,8 @@ static void subtract(Widget w, XEvent *ev, String *vector, Cardinal *count); static void sum(Widget w, XEvent *ev, String *vector, Cardinal *count); static void tangent(Widget w, XEvent *ev, String *vector, Cardinal *count); static void tenpower(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void xtrunc(Widget w, XEvent *ev, String *vector, Cardinal *count); +static void xor(Widget w, XEvent *ev, String *vector, Cardinal *count); static void XexchangeY(Widget w, XEvent *ev, String *vector, Cardinal *count); /* @@ -93,7 +102,9 @@ static void XexchangeY(Widget w, XEvent *ev, String *vector, Cardinal *count); XtActionsRec Actions[] = { {"add", add}, /* addition */ +{"and", and}, /* bitwise and */ {"back", back}, /* HP-specific backspace */ +{"base", base}, /* base conversion */ {"bell", bell}, /* ring bell */ {"clear", clearit}, /* TI-specific clear calculator state */ {"cosine", cosine}, /* trigonometric function cosine */ @@ -110,11 +121,14 @@ XtActionsRec Actions[] = { {"inverse", inverse}, /* inverse */ {"leftParen", leftParen}, /* TI-specific left parenthesis */ {"logarithm", logarithm}, /* logarithm base 10 */ +{"mod", mod}, /* modulus */ {"multiply", multiply}, /* multiplication */ {"naturalLog", naturalLog}, /* natural logarithm base e */ {"negate", negate}, /* change sign */ {"nop", nop}, /* no operation, rings bell */ +{"not", not}, /* bitwise not */ {"off", off}, /* clear state */ +{"or", or}, /* bitwise or */ {"pi", pi}, /* the number pi */ {"power", power}, /* raise to an arbitrary power */ {"quit", quit}, /* quit */ @@ -124,6 +138,8 @@ XtActionsRec Actions[] = { {"roll", roll}, /* HP-specific roll stack */ {"scientific", scientific}, /* scientfic notation (EE) */ {"selection", selection}, /* copy selection */ +{"shl", shl}, /* arithmetic shift left */ +{"shr", shr}, /* arithmetic shift right */ {"sine", sine}, /* trigonometric function sine */ {"square", square}, /* square */ {"squareRoot", squareRoot}, /* square root */ @@ -132,6 +148,8 @@ XtActionsRec Actions[] = { {"sum", sum}, /* memory summation */ {"tangent", tangent}, /* trigonometric function tangent */ {"tenpower", tenpower}, /* 10 raised to to an arbitrary power */ +{"trunc", xtrunc}, /* truncate to integer */ +{"xor", xor}, /* bitwise xor */ {"XexchangeY", XexchangeY} /* HP-specific exchange X and Y registers */ }; @@ -146,6 +164,14 @@ static void add(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void and(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kAND); + rpn ? twof(kAND) : twoop(kAND); + post_op(); +} + +/*ARGSUSED*/ static void back(Widget w, XEvent *ev, String *vector, Cardinal *count) { XCALC_PRE_OP(kBKSP); @@ -154,6 +180,14 @@ static void back(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void base(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kBASE); + change_base(); + post_op(); +} + +/*ARGSUSED*/ static void bell(Widget w, XEvent *ev, String *vector, Cardinal *count) { ringbell(); @@ -196,6 +230,7 @@ static void digit(Widget w, XEvent *ev, String *vector, Cardinal *count) { switch (vector[0][0]) { + case '0': XCALC_PRE_OP(kZERO); numeric(kZERO); break; case '1': XCALC_PRE_OP(kONE); numeric(kONE); break; case '2': XCALC_PRE_OP(kTWO); numeric(kTWO); break; case '3': XCALC_PRE_OP(kTHREE); numeric(kTHREE); break; @@ -205,7 +240,12 @@ static void digit(Widget w, XEvent *ev, String *vector, Cardinal *count) case '7': XCALC_PRE_OP(kSEVEN); numeric(kSEVEN); break; case '8': XCALC_PRE_OP(kEIGHT); numeric(kEIGHT); break; case '9': XCALC_PRE_OP(kNINE); numeric(kNINE); break; - case '0': XCALC_PRE_OP(kZERO); numeric(kZERO); break; + case 'A': XCALC_PRE_OP(kxA); numeric(kxA); break; + case 'B': XCALC_PRE_OP(kxB); numeric(kxB); break; + case 'C': XCALC_PRE_OP(kxC); numeric(kxC); break; + case 'D': XCALC_PRE_OP(kxD); numeric(kxD); break; + case 'E': XCALC_PRE_OP(kxE); numeric(kxE); break; + case 'F': XCALC_PRE_OP(kxF); numeric(kxF); break; } post_op(); } @@ -291,6 +331,14 @@ static void logarithm(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void mod(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kMOD); + rpn ? twof(kMOD) : twoop(kMOD); + post_op(); +} + +/*ARGSUSED*/ static void multiply(Widget w, XEvent *ev, String *vector, Cardinal *count) { XCALC_PRE_OP(kMUL); @@ -321,6 +369,14 @@ static void nop(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void not(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kNOT); + oneop(kNOT); + post_op(); +} + +/*ARGSUSED*/ static void off(Widget w, XEvent *ev, String *vector, Cardinal *count) { XCALC_PRE_OP(kOFF); @@ -329,6 +385,14 @@ static void off(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void or(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kOR); + rpn ? twof(kOR) : twoop(kOR); + post_op(); +} + +/*ARGSUSED*/ static void pi(Widget w, XEvent *ev, String *vector, Cardinal *count) { XCALC_PRE_OP(kPI); @@ -400,6 +464,22 @@ static void selection(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void shl(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kSHL); + rpn ? twof(kSHL) : twoop(kSHL); + post_op(); +} + +/*ARGSUSED*/ +static void shr(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kSHR); + rpn ? twof(kSHR) : twoop(kSHR); + post_op(); +} + +/*ARGSUSED*/ static void sine(Widget w, XEvent *ev, String *vector, Cardinal *count) { XCALC_PRE_OP(kSIN); @@ -464,6 +544,22 @@ static void tenpower(Widget w, XEvent *ev, String *vector, Cardinal *count) } /*ARGSUSED*/ +static void xtrunc(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kTRUNC); + oneop(kTRUNC); + post_op(); +} + +/*ARGSUSED*/ +static void xor(Widget w, XEvent *ev, String *vector, Cardinal *count) +{ + XCALC_PRE_OP(kXOR); + rpn ? twof(kXOR) : twoop(kXOR); + post_op(); +} + +/*ARGSUSED*/ static void XexchangeY(Widget w, XEvent *ev, String *vector, Cardinal *count) { XCALC_PRE_OP(kXXY); diff --git a/app-defaults/XCalc b/app-defaults/XCalc index 540df58..fa3684c 100644 --- a/app-defaults/XCalc +++ b/app-defaults/XCalc @@ -42,6 +42,15 @@ XCalc*bevel.screen.P.label: () XCalc*bevel.screen.P.fromHoriz: GRAD XCalc*bevel.screen.P.fromVert: LCD XCalc*bevel.screen.P.horizDistance: 2 +XCalc*bevel.screen.HEX.fromHoriz: P +XCalc*bevel.screen.HEX.fromVert: LCD +XCalc*bevel.screen.HEX.horizDistance: 1 +XCalc*bevel.screen.DEC.fromHoriz: P +XCalc*bevel.screen.DEC.fromVert: LCD +XCalc*bevel.screen.DEC.horizDistance: 1 +XCalc*bevel.screen.OCT.fromHoriz: P +XCalc*bevel.screen.OCT.fromVert: LCD +XCalc*bevel.screen.OCT.horizDistance: 1 !XCalc*ti.Geometry: 171x252 XCalc*ti.bevel.screen.LCD.width: 186 @@ -59,6 +68,12 @@ XCalc*ti.bevel.screen.LCD.translations: #replace\n\ None<Key>7:digit(7)\n\ None<Key>8:digit(8)\n\ None<Key>9:digit(9)\n\ + Shift<Key>a:digit(A)\n\ + Shift<Key>b:digit(B)\n\ + Shift<Key>c:digit(C)\n\ + Shift<Key>d:digit(D)\n\ + Shift<Key>e:digit(E)\n\ + Shift<Key>f:digit(F)\n\ <Key>KP_0:digit(0)\n\ <Key>KP_1:digit(1)\n\ <Key>KP_2:digit(2)\n\ @@ -71,6 +86,7 @@ XCalc*ti.bevel.screen.LCD.translations: #replace\n\ <Key>KP_9:digit(9)\n\ <Key>KP_Enter:equal()\n\ <Key>KP_Equal:equal()\n\ + <Key>Return:equal()\n\ <Key>KP_Multiply:multiply()\n\ <Key>KP_Add:add()\n\ <Key>KP_Subtract:subtract()\n\ @@ -87,6 +103,13 @@ XCalc*ti.bevel.screen.LCD.translations: #replace\n\ :<Key>(:leftParen()\n\ :<Key>):rightParen()\n\ :<Key>!:factorial()\n\ + :<Key>|:or()\n\ + :<Key>&:and()\n\ + :<Key><:shl()\n\ + :<Key>>:shr()\n\ + :<Key>~:not()\n\ + :<Key>%:mod()\n\ + <Key>x:xor()\n\ <Key>e:e()\n\ :<Key>^:power()\n\ <Key>p:pi()\n\ @@ -140,62 +163,95 @@ XCalc*ti.button14.translations: #override<Btn1Down>,<Btn1Up>:naturalLog()unset() XCalc*ti.button15.label: y^x XCalc*ti.button15.translations: #override<Btn1Down>,<Btn1Up>:power()unset() -XCalc*ti.button16.font: -adobe-symbol-*-*-*-*-*-120-*-*-*-*-*-* -XCalc*ti.button16.label: \160 -XCalc*ti.button16.translations: #override<Btn1Down>,<Btn1Up>:pi()unset() -XCalc*ti.button17.label: x! -XCalc*ti.button17.translations: #override<Btn1Down>,<Btn1Up>:factorial()unset() -XCalc*ti.button18.label: ( -XCalc*ti.button18.translations: #override<Btn1Down>,<Btn1Up>:leftParen()unset() -XCalc*ti.button19.label: ) -XCalc*ti.button19.translations: #override<Btn1Down>,<Btn1Up>:rightParen()unset() -XCalc*ti.button20.font: -adobe-symbol-*-*-*-*-*-120-*-*-*-*-*-* -XCalc*ti.button20.label: \270 -XCalc*ti.button20.translations: #override<Btn1Down>,<Btn1Up>:divide()unset() - -XCalc*ti.button21.label: STO -XCalc*ti.button21.translations: #override<Btn1Down>,<Btn1Up>:store()unset() -XCalc*ti.button22.label: 7 -XCalc*ti.button22.translations: #override<Btn1Down>,<Btn1Up>:digit(7)unset() -XCalc*ti.button23.label: 8 -XCalc*ti.button23.translations: #override<Btn1Down>,<Btn1Up>:digit(8)unset() -XCalc*ti.button24.label: 9 -XCalc*ti.button24.translations: #override<Btn1Down>,<Btn1Up>:digit(9)unset() -XCalc*ti.button25.label: * -XCalc*ti.button25.translations: #override<Btn1Down>,<Btn1Up>:multiply()unset() - -XCalc*ti.button26.label: RCL -XCalc*ti.button26.translations: #override<Btn1Down>,<Btn1Up>:recall()unset() -XCalc*ti.button27.label: 4 -XCalc*ti.button27.translations: #override<Btn1Down>,<Btn1Up>:digit(4)unset() -XCalc*ti.button28.label: 5 -XCalc*ti.button28.translations: #override<Btn1Down>,<Btn1Up>:digit(5)unset() -XCalc*ti.button29.label: 6 -XCalc*ti.button29.translations: #override<Btn1Down>,<Btn1Up>:digit(6)unset() -XCalc*ti.button30.label: - -XCalc*ti.button30.translations: #override<Btn1Down>,<Btn1Up>:subtract()unset() - -XCalc*ti.button31.label: SUM -XCalc*ti.button31.translations: #override<Btn1Down>,<Btn1Up>:sum()unset() -XCalc*ti.button32.label: 1 -XCalc*ti.button32.translations: #override<Btn1Down>,<Btn1Up>:digit(1)unset() -XCalc*ti.button33.label: 2 -XCalc*ti.button33.translations: #override<Btn1Down>,<Btn1Up>:digit(2)unset() -XCalc*ti.button34.label: 3 -XCalc*ti.button34.translations: #override<Btn1Down>,<Btn1Up>:digit(3)unset() -XCalc*ti.button35.label: + -XCalc*ti.button35.translations: #override<Btn1Down>,<Btn1Up>:add()unset() - -XCalc*ti.button36.label: EXC -XCalc*ti.button36.translations: #override<Btn1Down>,<Btn1Up>:exchange()unset() -XCalc*ti.button37.label: 0 -XCalc*ti.button37.translations: #override<Btn1Down>,<Btn1Up>:digit(0)unset() -XCalc*ti.button38.label: . -XCalc*ti.button38.translations: #override<Btn1Down>,<Btn1Up>:decimal()unset() -XCalc*ti.button39.label: +/- -XCalc*ti.button39.translations: #override<Btn1Down>,<Btn1Up>:negate()unset() -XCalc*ti.button40.label: = -XCalc*ti.button40.translations: #override<Btn1Down>,<Btn1Up>:equal()unset() +XCalc*ti.button16.label: not +XCalc*ti.button16.translations: #override<Btn1Down>,<Btn1Up>:not()unset() +XCalc*ti.button17.label: and +XCalc*ti.button17.translations: #override<Btn1Down>,<Btn1Up>:and()unset() +XCalc*ti.button18.label: or +XCalc*ti.button18.translations: #override<Btn1Down>,<Btn1Up>:or()unset() +XCalc*ti.button19.label: xor +XCalc*ti.button19.translations: #override<Btn1Down>,<Btn1Up>:xor()unset() +XCalc*ti.button20.label: trunc +XCalc*ti.button20.translations: #override<Btn1Down>,<Btn1Up>:trunc()unset() + +XCalc*ti.button21.font: -adobe-symbol-*-*-*-*-*-120-*-*-*-*-*-* +XCalc*ti.button21.label: \160 +XCalc*ti.button21.translations: #override<Btn1Down>,<Btn1Up>:pi()unset() +XCalc*ti.button22.label: x! +XCalc*ti.button22.translations: #override<Btn1Down>,<Btn1Up>:factorial()unset() +XCalc*ti.button23.label: ( +XCalc*ti.button23.translations: #override<Btn1Down>,<Btn1Up>:leftParen()unset() +XCalc*ti.button24.label: ) +XCalc*ti.button24.translations: #override<Btn1Down>,<Btn1Up>:rightParen()unset() +XCalc*ti.button25.label: base +XCalc*ti.button25.translations: #override<Btn1Down>,<Btn1Up>:base()unset() + +XCalc*ti.button26.label: shl +XCalc*ti.button26.translations: #override<Btn1Down>,<Btn1Up>:shl()unset() +XCalc*ti.button27.label: D +XCalc*ti.button27.translations: #override<Btn1Down>,<Btn1Up>:digit(D)unset() +XCalc*ti.button28.label: E +XCalc*ti.button28.translations: #override<Btn1Down>,<Btn1Up>:digit(E)unset() +XCalc*ti.button29.label: F +XCalc*ti.button29.translations: #override<Btn1Down>,<Btn1Up>:digit(F)unset() +XCalc*ti.button30.label: shr +XCalc*ti.button30.translations: #override<Btn1Down>,<Btn1Up>:shr()unset() + +XCalc*ti.button31.label: mod +XCalc*ti.button31.translations: #override<Btn1Down>,<Btn1Up>:mod()unset() +XCalc*ti.button32.label: A +XCalc*ti.button32.translations: #override<Btn1Down>,<Btn1Up>:digit(A)unset() +XCalc*ti.button33.label: B +XCalc*ti.button33.translations: #override<Btn1Down>,<Btn1Up>:digit(B)unset() +XCalc*ti.button34.label: C +XCalc*ti.button34.translations: #override<Btn1Down>,<Btn1Up>:digit(C)unset() +XCalc*ti.button35.font: -adobe-symbol-*-*-*-*-*-120-*-*-*-*-*-* +XCalc*ti.button35.label: \270 +XCalc*ti.button35.translations: #override<Btn1Down>,<Btn1Up>:divide()unset() + +XCalc*ti.button36.label: STO +XCalc*ti.button36.translations: #override<Btn1Down>,<Btn1Up>:store()unset() +XCalc*ti.button37.label: 7 +XCalc*ti.button37.translations: #override<Btn1Down>,<Btn1Up>:digit(7)unset() +XCalc*ti.button38.label: 8 +XCalc*ti.button38.translations: #override<Btn1Down>,<Btn1Up>:digit(8)unset() +XCalc*ti.button39.label: 9 +XCalc*ti.button39.translations: #override<Btn1Down>,<Btn1Up>:digit(9)unset() +XCalc*ti.button40.label: * +XCalc*ti.button40.translations: #override<Btn1Down>,<Btn1Up>:multiply()unset() + +XCalc*ti.button41.label: RCL +XCalc*ti.button41.translations: #override<Btn1Down>,<Btn1Up>:recall()unset() +XCalc*ti.button42.label: 4 +XCalc*ti.button42.translations: #override<Btn1Down>,<Btn1Up>:digit(4)unset() +XCalc*ti.button43.label: 5 +XCalc*ti.button43.translations: #override<Btn1Down>,<Btn1Up>:digit(5)unset() +XCalc*ti.button44.label: 6 +XCalc*ti.button44.translations: #override<Btn1Down>,<Btn1Up>:digit(6)unset() +XCalc*ti.button45.label: - +XCalc*ti.button45.translations: #override<Btn1Down>,<Btn1Up>:subtract()unset() + +XCalc*ti.button46.label: SUM +XCalc*ti.button46.translations: #override<Btn1Down>,<Btn1Up>:sum()unset() +XCalc*ti.button47.label: 1 +XCalc*ti.button47.translations: #override<Btn1Down>,<Btn1Up>:digit(1)unset() +XCalc*ti.button48.label: 2 +XCalc*ti.button48.translations: #override<Btn1Down>,<Btn1Up>:digit(2)unset() +XCalc*ti.button49.label: 3 +XCalc*ti.button49.translations: #override<Btn1Down>,<Btn1Up>:digit(3)unset() +XCalc*ti.button50.label: + +XCalc*ti.button50.translations: #override<Btn1Down>,<Btn1Up>:add()unset() + +XCalc*ti.button51.label: EXC +XCalc*ti.button51.translations: #override<Btn1Down>,<Btn1Up>:exchange()unset() +XCalc*ti.button52.label: 0 +XCalc*ti.button52.translations: #override<Btn1Down>,<Btn1Up>:digit(0)unset() +XCalc*ti.button53.label: . +XCalc*ti.button53.translations: #override<Btn1Down>,<Btn1Up>:decimal()unset() +XCalc*ti.button54.label: +/- +XCalc*ti.button54.translations: #override<Btn1Down>,<Btn1Up>:negate()unset() +XCalc*ti.button55.label: = +XCalc*ti.button55.translations: #override<Btn1Down>,<Btn1Up>:equal()unset() XCalc*ti.button1.horizDistance: 4 XCalc*ti.button1.vertDistance: 12 @@ -290,6 +346,38 @@ XCalc*ti.button39.fromVert: button34 XCalc*ti.button40.fromHoriz: button39 XCalc*ti.button40.fromVert: button35 +XCalc*ti.button41.horizDistance: 4 +XCalc*ti.button41.fromVert: button36 +XCalc*ti.button42.fromHoriz: button41 +XCalc*ti.button42.fromVert: button37 +XCalc*ti.button43.fromHoriz: button42 +XCalc*ti.button43.fromVert: button38 +XCalc*ti.button44.fromHoriz: button43 +XCalc*ti.button44.fromVert: button39 +XCalc*ti.button45.fromHoriz: button44 +XCalc*ti.button45.fromVert: button40 + +XCalc*ti.button46.horizDistance: 4 +XCalc*ti.button46.fromVert: button41 +XCalc*ti.button47.fromHoriz: button46 +XCalc*ti.button47.fromVert: button42 +XCalc*ti.button48.fromHoriz: button47 +XCalc*ti.button48.fromVert: button43 +XCalc*ti.button49.fromHoriz: button48 +XCalc*ti.button49.fromVert: button44 +XCalc*ti.button50.fromHoriz: button49 +XCalc*ti.button50.fromVert: button45 + +XCalc*ti.button51.horizDistance: 4 +XCalc*ti.button51.fromVert: button46 +XCalc*ti.button52.fromHoriz: button51 +XCalc*ti.button52.fromVert: button47 +XCalc*ti.button53.fromHoriz: button52 +XCalc*ti.button53.fromVert: button48 +XCalc*ti.button54.fromHoriz: button53 +XCalc*ti.button54.fromVert: button49 +XCalc*ti.button55.fromHoriz: button54 +XCalc*ti.button55.fromVert: button50 !XCalc*hp.Geometry: 336x164 XCalc*hp.bevel.screen.LCD.width: 186 @@ -43,7 +43,7 @@ jmp_buf env; * functions. Much of it is shared between the infix and rpn modes. */ -static int flagINV, flagPAREN, flagM, drgmode; /* display flags */ +static int flagINV, flagPAREN, flagM, drgmode, numbase; /* display flags */ static double drg2rad=M_PI/180.0; /* Conversion factors for trig funcs */ static double rad2drg=180.0/M_PI; @@ -94,17 +94,47 @@ strlcpy(char *dst, const char *src, size_t size) * is non-zero then an error has occurred. On some systems (e.g. Ultrix), * sscanf will call lower level routines that will set errno. */ - static void -parse_double (const char *src, const char *fmt, double *dp) +parse_double(double *dp) { + unsigned long n = 0; int olderrno = errno; - (void) sscanf (src, fmt, dp); + switch (numbase) { + case 8: + (void)sscanf(dispstr, "%lo", &n); + *dp = (double)n; + break; + case 16: + (void)sscanf(dispstr, "%lX", &n); + *dp = (double)n; + break; + default: + (void)sscanf(dispstr, "%lf", dp); + } + errno = olderrno; return; } +/** + * Format the given double according to the + * selected number base. + */ +static void +format_double(double n) +{ + switch (numbase) { + case 8: + snprintf(dispstr, sizeof(dispstr), "%lo", (long)n); + break; + case 16: + snprintf(dispstr, sizeof(dispstr), "%lX", (long)n); + break; + default: + snprintf(dispstr, sizeof(dispstr), "%.8g", n); + } +} /*********************************/ int pre_op(int keynum) @@ -181,12 +211,13 @@ void post_op(void) } #endif } + /*-------------------------------------------------------------------------*/ static void DrawDisplay(void) { - if (strlen(dispstr) > 12) { /* strip out some decimal digits */ - char *estr = strchr(dispstr,'e'); /* search for exponent part */ + if (strlen(dispstr) >= MAXDISP) { /* strip out some decimal digits */ + char *estr = index(dispstr,'e'); /* search for exponent part */ if (!estr) dispstr[12]='\0'; /* no exp, just trunc. */ else { char tmp[32]; @@ -204,6 +235,28 @@ DrawDisplay(void) setflag(XCalc_RADIAN, (drgmode==RAD)); setflag(XCalc_GRADAM, (drgmode==GRAD)); setflag(XCalc_PAREN, (flagPAREN)); + setflag(XCalc_HEX, (numbase==16)); + setflag(XCalc_DEC, (numbase==10)); + setflag(XCalc_OCT, (numbase==8)); +} + +/*-------------------------------------------------------------------------*/ +void +change_base(void) +{ + parse_double(&dnum); + + if (dnum >= 0) { + switch (numbase) { + case 8: numbase = 10; break; + case 10: numbase = 16; break; + case 16: numbase = 8; break; + } + + format_double(dnum); + } else strlcpy(dispstr, "error", sizeof(dispstr)); + + DrawDisplay(); } /*-------------------------------------------------------------------------*/ @@ -239,7 +292,7 @@ numeric(int keynum) case kRCL: PushNum(dnum); dnum = mem[cell]; - snprintf(dispstr, sizeof(dispstr), "%.8g", dnum); + format_double(dnum); lift_enabled = 1; entered = 1; clrdisp++; @@ -268,7 +321,9 @@ numeric(int keynum) if ((int) strlen(dispstr) >= MAXDISP) return; + st[0] = '\0'; switch (keynum){ + case kZERO: st[0] = '0'; break; case kONE: st[0] = '1'; break; case kTWO: st[0] = '2'; break; case kTHREE: st[0] = '3'; break; @@ -276,12 +331,20 @@ numeric(int keynum) case kFIVE: st[0] = '5'; break; case kSIX: st[0] = '6'; break; case kSEVEN: st[0] = '7'; break; - case kEIGHT: st[0] = '8'; break; - case kNINE: st[0] = '9'; break; - case kZERO: st[0] = '0'; break; - } - st[1] = '\0'; - strcat(dispstr,st); + case kEIGHT: if (numbase > 8) st[0] = '8'; break; + case kNINE: if (numbase > 8) st[0] = '9'; break; + case kxA: if (numbase > 10) st[0] = 'A'; break; + case kxB: if (numbase > 10) st[0] = 'B'; break; + case kxC: if (numbase > 10) st[0] = 'C'; break; + case kxD: if (numbase > 10) st[0] = 'D'; break; + case kxE: if (numbase > 10) st[0] = 'E'; break; + case kxF: if (numbase > 10) st[0] = 'F'; break; + } + + if (st[0] == '\0') + return; + st[1] = '\0'; + strcat(dispstr,st); DrawDisplay(); if (clrdisp && keynum != kZERO) @@ -433,7 +496,7 @@ twoop(int keynum) } if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); clrdisp=CLR=1; entered=Dpoint=exponent=0; @@ -451,7 +514,7 @@ twoop(int keynum) /* now, if the current op (keynum) is of higher priority than the lastop, the current op and number are just pushed on top - Priorities: (Y^X) > *,/ > +,- */ + Priorities: (Y^X) > *,/ > +,- > >>,<< > & > ^ > ~ */ if (priority(keynum) > priority(lastop)) { PushNum(dnum); @@ -466,10 +529,17 @@ twoop(int keynum) case kMUL: acc *= dnum; break; case kDIV: acc /= dnum; break; case kPOW: acc = pow(acc,dnum); break; - } + case kMOD: acc = (long)acc % (long)dnum; break; + case kAND: acc = (long)acc & (long)dnum; break; + case kOR: acc = (long)acc | (long)dnum; break; + case kXOR: acc = (long)acc ^ (long)dnum; break; + case kSHL: acc = (long)acc << (long)dnum; break; + case kSHR: acc = (long)acc >> (long)dnum; break; + } + PushNum(acc); PushOp(keynum); - snprintf(dispstr, sizeof(dispstr), "%.8g", acc); + format_double(acc); DrawDisplay(); dnum=acc; } @@ -491,7 +561,7 @@ twof(int keynum) if (!entered) return; if (entered==1) - parse_double(dispstr, "%lf", &dnum); + parse_double(&dnum); acc = PopNum(); switch(keynum) { case kADD: acc += dnum; break; @@ -499,9 +569,16 @@ twof(int keynum) case kMUL: acc *= dnum; break; case kDIV: acc /= dnum; break; case kPOW: acc = pow(acc,dnum); break; - case kXXY: PushNum(dnum); + case kXXY: PushNum(dnum); break; + case kMOD: acc = (long)acc % (long)dnum; break; + case kAND: acc = (long)acc & (long)dnum; break; + case kOR: acc = (long)acc | (long)dnum; break; + case kXOR: acc = (long)acc ^ (long)dnum; break; + case kSHL: acc = (long)acc << (long)dnum; break; + case kSHR: acc = (long)acc >> (long)dnum; break; } - snprintf(dispstr, sizeof(dispstr), "%.8g", acc); + + format_double(acc); DrawDisplay(); clrdisp++; Dpoint = exponent = 0; @@ -521,7 +598,7 @@ entrf(void) Dpoint=exponent=0; if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); entered=2; memop = kENTR; PushNum(dnum); @@ -539,7 +616,7 @@ equf(void) Dpoint=exponent=0; if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); entered=2; PushNum(dnum); @@ -562,12 +639,24 @@ equf(void) case kLPAR: flagPAREN--; PushNum(acc); break; + case kMOD: acc = (long)acc % (long)dnum; + break; + case kAND: acc = (long)acc & (long)dnum; + break; + case kOR: acc = (long)acc | (long)dnum; + break; + case kXOR: acc = (long)acc ^ (long)dnum; + break; + case kSHL: acc = (long)acc << (long)dnum; + break; + case kSHR: acc = (long)acc >> (long)dnum; + break; } dnum=acc; PushNum(dnum); } - snprintf(dispstr, sizeof(dispstr), "%.8g", dnum); + format_double(dnum); DrawDisplay(); } @@ -586,13 +675,13 @@ rollf(void) if (!entered) return; if (entered==1) - parse_double(dispstr, "%lf", &dnum); + parse_double(&dnum); entered = 2; lift_enabled = 1; RollNum(flagINV); flagINV=0; clrdisp++; - snprintf(dispstr, sizeof(dispstr), "%.8g", dnum); + format_double(dnum); DrawDisplay(); } @@ -610,7 +699,7 @@ rparf(void) Dpoint=exponent=0; if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); entered=2; PushNum(dnum); @@ -629,6 +718,18 @@ rparf(void) break; case kPOW: acc = pow(acc,dnum); break; + case kMOD: acc = (long)acc % (long)dnum; + break; + case kAND: acc = (long)acc & (long)dnum; + break; + case kOR: acc = (long)acc | (long)dnum; + break; + case kXOR: acc = (long)acc ^ (long)dnum; + break; + case kSHL: acc = (long)acc << (long)dnum; + break; + case kSHR: acc = (long)acc >> (long)dnum; + break; } dnum=acc; PushNum(dnum); @@ -636,7 +737,7 @@ rparf(void) (void) PopNum(); flagPAREN--; entered=2; - snprintf(dispstr, sizeof(dispstr), "%.8g", dnum); + format_double(dnum); DrawDisplay(); } @@ -645,7 +746,7 @@ drgf(void) { if (flagINV) { if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); switch (drgmode) { case DEG: dnum=dnum*M_PI/180.0; break; case RAD: dnum=dnum*200.0/M_PI; break; @@ -654,7 +755,7 @@ drgf(void) entered=2; clrdisp=1; flagINV=0; - snprintf(dispstr, sizeof(dispstr), "%.8g", dnum); + format_double(dnum); } flagINV=0; @@ -685,7 +786,7 @@ memf(int keynum) { memop = keynum; if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); entered = 2; clrdisp++; lift_enabled = 0; @@ -698,7 +799,7 @@ oneop(int keynum) double dtmp; if (entered==1) - parse_double(dispstr,"%lf",&dnum); + parse_double(&dnum); entered = 2; switch (keynum) { /* do the actual math fn. */ @@ -741,6 +842,8 @@ oneop(int keynum) for (j=1,dnum=1.0; j<=i; j++) dnum*=(float) j; break; + case kNOT: dnum = ~(long)dnum; break; + case kTRUNC: dnum = trunc(dnum); break; } if (entered==3) { /* error */ @@ -753,7 +856,7 @@ oneop(int keynum) clrdisp=1; flagINV=0; lift_enabled = 1; - snprintf(dispstr, sizeof(dispstr), "%.8g", dnum); + format_double(dnum); DrawDisplay(); } @@ -899,12 +1002,18 @@ priority(int op) /*******/ { switch (op) { - case kPOW: return(2); + case kPOW: return(6); case kMUL: - case kDIV: return(1); + case kDIV: + case kMOD: return(5); case kADD: - case kSUB: return(0); - } + case kSUB: return(4); + case kSHL: + case kSHR: return(3); + case kAND: return(2); + case kXOR: return(1); + case kOR: return(0); + } return 0; } @@ -915,12 +1024,16 @@ ResetCalc(void) /********/ { flagM=flagINV=flagPAREN=0; drgmode=DEG; + numbase=(!numbase ? 10 : numbase); setflag(XCalc_MEMORY, False); setflag(XCalc_INVERSE, False); setflag(XCalc_PAREN, False); setflag(XCalc_RADIAN, False); setflag(XCalc_GRADAM, False); setflag(XCalc_DEGREE, True); + setflag(XCalc_HEX, False); + setflag(XCalc_DEC, True); + setflag(XCalc_OCT, False); strlcpy(dispstr, "0", sizeof(dispstr)); draw(dispstr); ClearStacks(); @@ -74,7 +74,7 @@ static Display *dpy = NULL; /* connection to the X server */ static Widget toplevel=NULL; /* top level shell widget */ static Widget calculator=NULL; /* an underlying form widget */ static Widget LCD = NULL; /* liquid crystal display */ -static Widget ind[6]; /* mode indicators in the screen */ +static Widget ind[9]; /* mode indicators in the screen */ static char selstr[LCD_STR_LEN]; /* storage for selections from the LCD */ /* checkerboard used in mono mode */ static XtAppContext xtcontext; /* Toolkit application context */ @@ -221,6 +221,18 @@ static void create_display(Widget parent) /* () - the parenthesis indicator */ ind[XCalc_PAREN] = XtCreateManagedWidget("P", labelWidgetClass, screen, args, XtNumber(args)); + + /* HEX - the hexadecimal (base 16) indicator */ + ind[XCalc_HEX] = XtCreateManagedWidget("HEX", labelWidgetClass, screen, + args, XtNumber(args)); + + /* DEC - the hexadecimal (base 16) indicator */ + ind[XCalc_DEC] = XtCreateManagedWidget("DEC", labelWidgetClass, screen, + args, XtNumber(args)); + + /* OCT - the octal (base 8) indicator */ + ind[XCalc_OCT] = XtCreateManagedWidget("OCT", labelWidgetClass, screen, + args, XtNumber(args)); } /* @@ -240,7 +252,10 @@ static void create_keypad(Widget parent) "button21","button22","button23","button24","button25", "button26","button27","button28","button29","button30", "button31","button32","button33","button34","button35", - "button36","button37","button38","button39","button40" + "button36","button37","button38","button39","button40", + "button41","button42","button43","button44","button45", + "button46","button47","button48","button49","button50", + "button51","button52","button53","button54","button55", }; register int i; int n = XtNumber(Keyboard); @@ -102,6 +102,21 @@ from the X Consortium. #define kROLL 44 /* roll stack */ #define kNOP 45 /* no operation */ #define kBKSP 46 /* backspace */ +#define kAND 47 /* bitwise and */ +#define kBASE 48 /* base conversion */ +#define kMOD 49 /* modulus */ +#define kNOT 50 /* bitwise not (ones compliment) */ +#define kOR 51 /* bitwise or */ +#define kSHL 52 /* arithmetic shift left */ +#define kSHR 53 /* arithmetic shift right */ +#define kXOR 54 /* bitwise xor */ +#define kTRUNC 55 /* truncate to integer */ +#define kxA 56 /* 0xa */ +#define kxB 57 /* 0xb */ +#define kxC 58 /* 0xc */ +#define kxD 59 /* 0xd */ +#define kxE 60 /* 0xe */ +#define kxF 61 /* 0xf */ #define XCalc_MEMORY 0 /* memory indicator */ #define XCalc_INVERSE 1 /* inverse function indicator */ @@ -109,6 +124,9 @@ from the X Consortium. #define XCalc_RADIAN 3 /* radian indicator */ #define XCalc_GRADAM 4 /* grad indicator */ #define XCalc_PAREN 5 /* parenthesis indicator */ +#define XCalc_HEX 6 /* hexadecimal (base 16) indicator */ +#define XCalc_DEC 7 /* decimal (base 10) indicator */ +#define XCalc_OCT 8 /* octal (base 8) indicator */ /* actions.c */ extern XtActionsRec Actions[]; @@ -121,6 +139,7 @@ extern void fail_op(void); extern int pre_op(int keynum); extern void post_op(void); +extern void change_base(void); extern void numeric(int keynum); extern void bkspf(void); extern void decf(void); |