|
|
1.1 ! root 1: lifedemo = proc () ! 2: qi = sequence[int] ! 3: ai = array[int] ! 4: ab = array[bool] ! 5: pwidth = 8 ! 6: bwidth: int := int$parse(xdemo_default("life", "BorderWidth")) ! 7: except when not_found, overflow, bad_format: bwidth := 2 end ! 8: back: x_pixmap := x_display$white() ! 9: bdr: x_pixmap := x_display$black() ! 10: backpix: int := WhitePixel ! 11: forepix: int := BlackPixel ! 12: mousepix: int := BlackPixel ! 13: if x_display$cells() > 2 ! 14: then begin ! 15: r, g, b: int := x_parse_color(xdemo_default("life", "Border")) ! 16: bdr := x_pixmap$tile(x_display$alloc_color(r, g, b)) ! 17: end except when not_found: end ! 18: begin ! 19: r, g, b: int := x_parse_color(xdemo_default("life", "Background")) ! 20: backpix := x_display$alloc_color(r, g, b) ! 21: back := x_pixmap$tile(backpix) ! 22: end except when not_found: end ! 23: begin ! 24: r, g, b: int := x_parse_color(xdemo_default("life", "Foreground")) ! 25: forepix := x_display$alloc_color(r, g, b) ! 26: mousepix := forepix ! 27: end except when not_found: end ! 28: begin ! 29: r, g, b: int := x_parse_color(xdemo_default("life", "Mouse")) ! 30: mousepix := x_display$alloc_color(r, g, b) ! 31: end except when not_found: end ! 32: end ! 33: f: x_font := x_font$create("8x13") ! 34: w: x_window, cwidth, cheight: int := x_tcons("life", back, bdr, ! 35: xdemo_geometry(), "=40x40+1+1", ! 36: f, 8, 8, 1, 3, 3, bwidth) ! 37: x_font$destroy(f) ! 38: x_window$set_resize(w, 1, 8, 1, 8) ! 39: w.name := "life" ! 40: w.input := ButtonPressed + UnmapWindow ! 41: x_window$map(w) ! 42: w.input := ButtonPressed + ExposeRegion + UnmapWindow ! 43: cr: x_cursor := x_cursor$scons(arrow_width, arrow_height, ! 44: arrow, arrow_mask, ! 45: backpix, mousepix, ! 46: arrow_x, arrow_y, GXcopy) ! 47: w.cursor := cr ! 48: stopped: bool := false ! 49: ev: event := x_input$empty_event() ! 50: while true do ! 51: sx, sy, width, height, bw, ms, wk: int, iw: x_window := x_window$query(w) ! 52: if height <= 30 cor width <= 30 ! 53: then x_window$destroy(w) ! 54: return ! 55: end ! 56: x_window$clear(w) ! 57: width := (width - 1) / pwidth ! 58: prob: int := int$min(10, width / 2) ! 59: height := (height - 1) / pwidth + 2 ! 60: span: int := width * height ! 61: arena: ab := ab$fill(0, span, false) ! 62: xcoords: ai := ai$fill(0, span, 0) ! 63: ycoords: ai := ai$fill(0, span, 0) ! 64: for point: int in int$from_to(0, span - 1) do ! 65: xcoords[point] := (point // width) * pwidth + 1 ! 66: ycoords[point] := (point / width - 1) * pwidth + 1 ! 67: end ! 68: neighbor_list: ai := ai$predict(1, span / 4) ! 69: neighbors: ai := ai$fill(0, span, 0) ! 70: neighbor_map: ai := ai$fill(0, span, 0) ! 71: generation: int := 1 ! 72: offset: qi := qi$[-(width + 1), -width, -(width - 1), -1, ! 73: 1, width - 1, width, width + 1] ! 74: change_sets: ai := ai$predict(1, span) ! 75: change_clears: ai := ai$predict(1, span) ! 76: span := span - width ! 77: while true do ! 78: while stopped cor ! 79: (ai$empty(change_sets) cand ai$empty(change_clears)) cor ! 80: x_input$pending() do ! 81: x_input$deq(ev) ! 82: if ev.kind = UnmapWindow ! 83: then x_input$deq(ev) end ! 84: if ev.kind = ButtonPressed cand ev.value = LeftButton ! 85: then for point: int in int$from_to(width, span - 1) do ! 86: if random$next(prob) ~= 0 ! 87: then continue end ! 88: if neighbor_map[point] ~= generation ! 89: then neighbor_map[point] := generation ! 90: ai$addh(neighbor_list, point) ! 91: end ! 92: if arena[point] ! 93: then ai$addh(change_clears, point) ! 94: else ai$addh(change_sets, point) ! 95: end ! 96: end ! 97: break ! 98: elseif ev.kind = ButtonPressed cand ev.value = MiddleButton ! 99: then stopped := ~stopped ! 100: elseif ev.kind = ButtonPressed cand ev.value = RightButton ! 101: then for i: int in int$from_to(0, span - 1) do ! 102: arena[i] := false ! 103: neighbors[i] := 0 ! 104: neighbor_map[i] := 0 ! 105: end ! 106: generation := 1 ! 107: x_window$clear(w) ! 108: ai$trim(change_sets, 1, 0) ! 109: ai$trim(change_clears, 1, 0) ! 110: elseif ev.kind = ExposeWindow cand ! 111: (width ~= (ev.x - 1) / pwidth cor ! 112: height ~= (ev.y - 1) / pwidth + 2) ! 113: then exit changed ! 114: else x1: int := ev.x ! 115: y1: int := ev.y ! 116: x: int := (x1 + ev.x0 - 1) / pwidth ! 117: y: int := (y1 + ev.y0 - 1) / pwidth ! 118: x1 := x1 / pwidth ! 119: y1 := y1 / pwidth ! 120: for i: int in int$from_to(x1, x) do ! 121: for j: int in int$from_to(y1, y) do ! 122: point: int := j * width + i ! 123: if arena[point] ! 124: then x_window$pix_set(w, forepix, ! 125: xcoords[point], ! 126: ycoords[point], ! 127: pwidth - 1, pwidth - 1) ! 128: end except when bounds: end ! 129: end ! 130: end ! 131: end ! 132: end ! 133: for point: int in ai$elements(change_clears) do ! 134: x_window$pix_set(w, backpix, ! 135: xcoords[point], ycoords[point], ! 136: pwidth - 1, pwidth - 1) ! 137: arena[point] := false ! 138: for i: int in qi$elements(offset) do ! 139: begin ! 140: index: int := point + i ! 141: neighbors[index] := neighbors[index] - 1 ! 142: if neighbor_map[index] ~= generation ! 143: then neighbor_map[index] := generation ! 144: ai$addh(neighbor_list, index) ! 145: end ! 146: end except when bounds: end ! 147: end ! 148: end ! 149: ai$trim(change_clears, 1, 0) ! 150: for point: int in ai$elements(change_sets) do ! 151: x_window$pix_set(w, forepix, ! 152: xcoords[point], ycoords[point], ! 153: pwidth - 1, pwidth - 1) ! 154: arena[point] := true ! 155: for i:int in qi$elements(offset) do ! 156: begin ! 157: index: int := point + i ! 158: neighbors[index] := neighbors[index] + 1 ! 159: if neighbor_map[index] ~= generation ! 160: then neighbor_map[index] := generation ! 161: ai$addh(neighbor_list, index) ! 162: end ! 163: end except when bounds: continue end ! 164: end ! 165: end ! 166: ai$trim(change_sets, 1, 0) ! 167: generation := generation + 1 ! 168: for point: int in ai$elements(neighbor_list) do ! 169: n: int := neighbors[point] ! 170: if n = 3 ! 171: then if ~arena[point] cand ! 172: point >= width cand point < span ! 173: then ai$addh(change_sets, point) end ! 174: elseif n ~= 2 ! 175: then if arena[point] ! 176: then ai$addh(change_clears, point) end ! 177: end ! 178: end ! 179: ai$trim(neighbor_list, 1, 0) ! 180: end except when changed: end ! 181: end ! 182: end lifedemo
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.