Вы не можете выбрать более 25 тем Темы должны начинаться с буквы или цифры, могут содержать дефисы(-) и должны содержать не более 35 символов.

162 строки
3.9KB

  1. /* vscreen.c - screen and keyboard for the c64 vim clone.
  2. *
  3. * The editor writes straight into the screen matrix at $0400 and colour ram at
  4. * $d800 rather than going through the kernal, and it selects the lower/upper
  5. * case character set at $1800 so that petscii $41-$5a draws as real lowercase.
  6. *
  7. * Everything here returns int, so the other compilation unit can call these
  8. * without declaring them (power c is K&R C).
  9. */
  10. char *scr; /* screen matrix, $0400 */
  11. char *colr; /* colour ram, $d800 */
  12. /* petscii byte -> screen code */
  13. s2v(p)
  14. int p;
  15. {
  16. if (p >= 0xc0) return p - 0x80;
  17. if (p >= 0xa0) return p - 0x40;
  18. if (p >= 0x60) return p - 0x20;
  19. if (p >= 0x40) return p - 0x40;
  20. return p;
  21. }
  22. /* raw screen code at row r, column c */
  23. sraw(r, c, v)
  24. int r, c, v;
  25. {
  26. int i;
  27. if (r < 0) return 0;
  28. if (r > 24) return 0;
  29. if (c < 0) return 0;
  30. if (c > 39) return 0;
  31. i = r * 40 + c;
  32. scr[i] = v;
  33. colr[i] = 1;
  34. return 0;
  35. }
  36. /* one petscii character */
  37. spc(r, c, p)
  38. int r, c, p;
  39. {
  40. sraw(r, c, s2v(p));
  41. return 0;
  42. }
  43. /* one petscii character, inverted: the cursor and the status row */
  44. srpc(r, c, p)
  45. int r, c, p;
  46. {
  47. sraw(r, c, s2v(p) + 128);
  48. return 0;
  49. }
  50. /* a reversed space, for the cursor sitting past the end of a line */
  51. sblk(r, c)
  52. int r, c;
  53. {
  54. sraw(r, c, 160);
  55. return 0;
  56. }
  57. /* a zero terminated petscii string */
  58. sps(r, c, s)
  59. int r, c;
  60. char *s;
  61. {
  62. while (*s) spc(r, c++, *s++);
  63. return 0;
  64. }
  65. /* n blanks from (r,c) */
  66. sclr(r, c, n)
  67. int r, c, n;
  68. {
  69. while (n-- > 0) sraw(r, c++, 32);
  70. return 0;
  71. }
  72. /* take over the machine: black on blue, lower case, no blinking cursor */
  73. sinit()
  74. {
  75. int i;
  76. char *p;
  77. scr = (char *) 0x0400;
  78. colr = (char *) 0xd800;
  79. p = (char *) 0xd018;
  80. *p = 0x17;
  81. p = (char *) 0xd020;
  82. *p = 0;
  83. p = (char *) 0xd021;
  84. *p = 6;
  85. p = (char *) 0x00cc; /* kernal cursor blink: non-zero = off */
  86. *p = 1;
  87. p = (char *) 0x0091; /* run/stop flag: drop whatever boot left */
  88. *p = 0;
  89. p = (char *) 0x028a; /* key repeat: c64 default, cursor keys */
  90. *p = 0; /* only (the power c shell leaves all on) */
  91. for (i = 0; i < 1000; i++) {
  92. scr[i] = 32;
  93. colr[i] = 1;
  94. }
  95. return 0;
  96. }
  97. /* give the machine back the way basic expects it */
  98. sdone()
  99. {
  100. char *p;
  101. char a, x, y;
  102. p = (char *) 0xd018;
  103. *p = 0x15;
  104. p = (char *) 0xd020;
  105. *p = 14;
  106. p = (char *) 0xd021;
  107. *p = 6;
  108. /* do not return to basic: power c owns zero page 43-74, which is where
  109. basic keeps its program and variable pointers, so basic carries on with
  110. garbage and prints a mangled error instead of READY. restart the
  111. machine through the kernal reset instead - banner and READY, like
  112. switching on. the file has been saved (or abandoned with :q!) by now. */
  113. a = 0;
  114. x = 0;
  115. y = 0;
  116. sys(0xfce2, &a, &x, &y); /* never comes back */
  117. return 0;
  118. }
  119. /* ---------------------------------------------------------------- keyboard
  120. *
  121. * Keys come straight out of the kernal's keyboard buffer: $c6 says how many
  122. * are waiting and they queue from $0277. The kernal's own irq handler scans
  123. * the keyboard matrix and fills that buffer, so this gets each press as it
  124. * happens - and it also catches anything typed before the program started.
  125. *
  126. * (GETIN through sys() once "crashed" - but that was sys() called with the
  127. * c128 bank argument; on the c64 it is sys(addr, &a, &x, &y).) And the library's getchar() is line buffered - it
  128. * echoes through the screen editor and only hands characters over after RETURN.
  129. */
  130. /* next key, or 0 if none is waiting. the pop runs in machine code with irqs
  131. masked, so the kernal cannot append a key half way through the shift */
  132. skeyp()
  133. {
  134. return mlkey();
  135. }
  136. /* wait for a key */
  137. skey()
  138. {
  139. int k;
  140. for (;;) {
  141. k = skeyp();
  142. if (k != 0) return k;
  143. }
  144. }

Powered by TurnKey Linux.