accumulate
generated by JSDoc 3.5.5 from
Github repository js-slang
- on Sun Mar 29 2020 14:25:21 GMT+0800 (Singapore Standard Time)
+ on Tue Apr 07 2020 00:42:59 GMT+0800 (Singapore Standard Time)
diff --git a/package.json b/package.json
index eddd4a97c..e3c54073a 100644
--- a/package.json
+++ b/package.json
@@ -35,7 +35,7 @@
"test": "jest",
"test-coveralls": "jest --coverage --coverageReporters=text-lcov | coveralls",
"tslint": "tslint -t verbose \"src/**/*.{ts,tsx}\"",
- "jsdoc": "./scripts/jsdoc.sh"
+ "jsdoc": "./scripts/jsdoc.sh && python ./scripts/updateAutocompleteDocs.py"
},
"repository": {
"type": "git",
@@ -49,6 +49,7 @@
"@types/jest": "^25.1.1",
"@types/node": "^13.7.0",
"coveralls": "^3.0.2",
+ "escodegen": "^1.14.1",
"husky": "^2.3.0",
"jest": "^23.6.0",
"jest-html-reporter": "^2.8.2",
diff --git a/scripts/updateAutocompleteDocs.py b/scripts/updateAutocompleteDocs.py
new file mode 100644
index 000000000..d7850f4c7
--- /dev/null
+++ b/scripts/updateAutocompleteDocs.py
@@ -0,0 +1,118 @@
+from lxml import etree, html
+from pathlib import Path
+import os
+import re
+import json
+
+CONST_DECL = "const"
+FUNC_DECL = "func"
+
+
+base_dir = "docs/source"
+src_filename = "global.html"
+out_dir = "src/editors/ace/docTooltip"
+
+
+def new_title_node(title):
+ node = etree.Element("h4")
+ node.text = title
+ return node
+
+
+def build_description_html(description_div):
+ description_html = html.tostring(description_div).decode("utf-8")
+
+ # There's a whole bunch of newlines between sections for some reason.
+ # Main reason for this is to avoid double newlines inside code blocks.
+ description_html = re.sub("\n+", "\n", description_html)
+
+ return description_html
+
+
+def process_constant(namespace, element):
+ header = element.find('./h4')
+ raw_name = "".join(header.itertext())
+ fields = raw_name.split()[1:] # first result just says (constant)
+
+ name = header.attrib["id"]
+ title = "".join(fields)
+ if not title: # Some runes have no title
+ title = name
+
+ title_node = new_title_node(title)
+
+ description_node = element.find('./div[@class="description"]')
+
+ description_div = etree.Element("div")
+ description_div.append(title_node)
+ description_div.append(description_node)
+
+ description_html = build_description_html(description_div)
+
+ namespace[name] = {"title": title,
+ "description": description_html, "meta": CONST_DECL}
+
+
+def process_function(namespace, element):
+ header = element.find('./h4')
+ title = "".join(header.itertext())
+ name = header.attrib["id"]
+
+ title_node = new_title_node(title)
+
+ description_node = element.find('./div[@class="description"]')
+
+ description_div = etree.Element("div")
+ description_div.append(title_node)
+ description_div.append(description_node)
+
+ description_html = build_description_html(description_div)
+
+ namespace[name] = {"title": title,
+ "description": description_html, "meta": FUNC_DECL}
+
+
+def process_dir_globals(target):
+ infile = os.path.join(base_dir, target, src_filename)
+ with open(infile) as f:
+ contents = "\n".join(f.readlines())
+ try:
+ tree = etree.HTML(contents)
+ except Exception as e:
+ print(infile, "failed", e)
+ return
+
+ names = {}
+
+ constants = tree.findall('.//div[@class="constant-entry"]')
+ for c in constants:
+ process_constant(names, c)
+
+ functions = tree.findall('.//div[@class="function-entry"]')
+ for f in functions:
+ process_function(names, f)
+
+ Path(out_dir).mkdir(parents=True, exist_ok=True)
+ outfile = os.path.join(out_dir, target + ".json")
+ with open(outfile, "w") as f:
+ json.dump(names, f, indent=2)
+
+# Folder names for jsdoc html
+targets = [
+ "source_1",
+ "source_2",
+ "source_3",
+ "source_3_concurrent",
+ "source_4",
+ "External libraries",
+]
+
+for target in targets:
+ if not os.path.exists(base_dir):
+ print("""\
+ Error: path to jsdoc html is invalid.
+ Ensure that this script is run from the project root and documentation has been generated\
+ """)
+ exit(1)
+
+ process_dir_globals(target)
diff --git a/src/editors/ace/docTooltip/External libraries.json b/src/editors/ace/docTooltip/External libraries.json
new file mode 100644
index 000000000..2804fe53f
--- /dev/null
+++ b/src/editors/ace/docTooltip/External libraries.json
@@ -0,0 +1,532 @@
+{
+ "blank": {
+ "title": "blank",
+ "description": "blank
\n primitive Rune in the rune of a blank square\n
\n
",
+ "meta": "const"
+ },
+ "circle": {
+ "title": "circle",
+ "description": "circle
\n primitive Rune in the rune of a circle\n
\n
",
+ "meta": "const"
+ },
+ "corner": {
+ "title": "corner",
+ "description": "corner
\n primitive Rune with black triangle,\nfilling upper right corner\n
\n
",
+ "meta": "const"
+ },
+ "heart": {
+ "title": "heart",
+ "description": "heart
\n primitive Rune in the rune of a heart\n
\n
",
+ "meta": "const"
+ },
+ "nova": {
+ "title": "nova",
+ "description": "nova
\n primitive Rune in the rune of two overlapping\ntriangles, residing in the upper half\nof\n
\n
",
+ "meta": "const"
+ },
+ "pentagram": {
+ "title": "pentagram",
+ "description": "pentagram
\n primitive Rune in the rune of a pentagram\n
\n
",
+ "meta": "const"
+ },
+ "rcross": {
+ "title": "rcross",
+ "description": "rcross
\n primitive Rune in the rune of a \nsmallsquare inside a large square,\neach diagonally split into a\nblack and white half\n
\n
",
+ "meta": "const"
+ },
+ "ribbon": {
+ "title": "ribbon",
+ "description": "ribbon
\n primitive Rune in the rune of a ribbon\nwinding outwards in an anticlockwise spiral\n
\n
",
+ "meta": "const"
+ },
+ "sail": {
+ "title": "sail",
+ "description": "sail
\n primitive Rune in the rune of a sail\n
\n
",
+ "meta": "const"
+ },
+ "square": {
+ "title": "square",
+ "description": "square
\n primitive Rune in the rune of a full square\n
\n
",
+ "meta": "const"
+ },
+ "adsr": {
+ "title": "adsr(attack_ratio, decay_ratio, sustain_level, release_ratio) \u2192 {function}",
+ "description": "adsr(attack_ratio, decay_ratio, sustain_level, release_ratio) → {function}
\n Returns an envelope: a function from Sound to Sound.\nWhen the envelope is applied to a Sound, it returns\na new Sound that results from applying ADSR to\nthe given Sound. The Attack, Sustain and\nRelease ratios are given in the first, second and fourth\narguments, and the Sustain level is given in \nthe third argument as a fraction between 0 and 1.\n
\n
",
+ "meta": "func"
+ },
+ "anaglyph": {
+ "title": "anaglyph(rune) \u2192 {Picture}",
+ "description": "anaglyph(rune) → {Picture}
\n turns a given Rune into an Anaglyph\n
\n
",
+ "meta": "func"
+ },
+ "apply_filter": {
+ "title": "apply_filter(filter) \u2192 {undefined}",
+ "description": "apply_filter(filter) → {undefined}
\n Installs a given filter to be used to transform\nthe images that the camera captures into images\ndisplayed on the screen. A filter is a function\nthat is applied to two two-dimensional arrays\nof Pixels: the source image and the destination\nimage.\n
\n
",
+ "meta": "func"
+ },
+ "arc": {
+ "title": "arc(t) \u2192 {Point}",
+ "description": "arc(t) → {Point}
\n this function is a curve: a function from a\nfraction t to a point. The points lie on the\nright half of the unit circle. They start at Point (0,1) when\nt is 0. When t is 0.5, they reach Point (1,0),\nwhen t is 1, they reach Point (0, -1).\n
\n
",
+ "meta": "func"
+ },
+ "bell": {
+ "title": "bell(note, duration) \u2192 {Sound}",
+ "description": "bell(note, duration) → {Sound}
\n returns a Sound that is reminiscent of a bell, playing\na given note for a given duration
of seconds\n
\n
",
+ "meta": "func"
+ },
+ "beside": {
+ "title": "beside(rune1, rune2) \u2192 {Rune}",
+ "description": "beside(rune1, rune2) → {Rune}
\n makes a new Rune from two given Runes by\nplacing the first on the left of the second,\nboth occupying equal portions of the width \nof the result\n
\n
",
+ "meta": "func"
+ },
+ "beside_frac": {
+ "title": "beside_frac(frac, rune1, rune2) \u2192 {Rune}",
+ "description": "beside_frac(frac, rune1, rune2) → {Rune}
\n makes a new Rune from two given Runes by\nplacing the first on the left of the second\nsuch that the first one occupies frac \nportion of the width of the result and \nthe second the rest\n
\n
",
+ "meta": "func"
+ },
+ "black": {
+ "title": "black(rune) \u2192 {Rune}",
+ "description": "black(rune) → {Rune}
\n colors the given rune black.\n
\n
",
+ "meta": "func"
+ },
+ "blue": {
+ "title": "blue(rune) \u2192 {Rune}",
+ "description": "blue(rune) → {Rune}
\n colors the given rune blue.\n
\n
",
+ "meta": "func"
+ },
+ "blue_of": {
+ "title": "blue_of(Pixel) \u2192 {Number}",
+ "description": "blue_of(Pixel) → {Number}
\n Returns the blue component of a given Pixel px
\n
\n
",
+ "meta": "func"
+ },
+ "brown": {
+ "title": "brown(rune) \u2192 {Rune}",
+ "description": "brown(rune) → {Rune}
\n colors the given rune brown.\n
\n
",
+ "meta": "func"
+ },
+ "cello": {
+ "title": "cello(note, duration) \u2192 {Sound}",
+ "description": "cello(note, duration) → {Sound}
\n returns a Sound that is reminiscent of a cello, playing\na given note for a given duration
of seconds\n
\n
",
+ "meta": "func"
+ },
+ "color": {
+ "title": "color(rune, r, g, b) \u2192 {Rune}",
+ "description": "color(rune, r, g, b) → {Rune}
\n adds color to rune by specifying \nthe red, green, blue (RGB) value, ranging from 0.0 to 1.0.\nRGB is additive: if all values are 1, the color is white,\nand if all values are 0, the color is black.\n
\n
",
+ "meta": "func"
+ },
+ "connect_ends": {
+ "title": "connect_ends(curve1, curve2) \u2192 {Curve}",
+ "description": "connect_ends(curve1, curve2) → {Curve}
\n this function is a binary Curve operator: It\ntakes two Curves as arguments and returns\na new Curve. The two Curves are combined\nby using the full first Curve for the first portion\nof the result and by using the full second Curve for the second\nportion of the result.\nThe second Curve is translated such that its point\nat fraction 0 is the same as the Point of the first\nCurve at fraction 1.\n
\n
",
+ "meta": "func"
+ },
+ "connect_rigidly": {
+ "title": "connect_rigidly(curve1, curve2) \u2192 {Curve}",
+ "description": "connect_rigidly(curve1, curve2) → {Curve}
\n this function is a binary Curve operator: It\ntakes two Curves as arguments and returns\na new Curve. The two Curves are combined\nby using the full first Curve for the first portion\nof the result and by using the full second Curve for the \nsecond portion of the result.\nThe second Curve is not changed, and therefore\nthere might be a big jump in the middle of the\nresult Curve.\n
\n
",
+ "meta": "func"
+ },
+ "consecutively": {
+ "title": "consecutively(sounds) \u2192 {Sound}",
+ "description": "consecutively(sounds) → {Sound}
\n makes a new sound by combining the sounds in a given\nlist so that\nthey are arranged consecutively. Let us say the durations\nof the sounds are d1
, ..., dn
and the wave \nfunctions are w1
, ..., wn
. Then the resulting\nsound has the duration of the sum of d1
, ..., dn
.\nThe wave function w
of the resulting sound uses w1
for the first\nd1
seconds, w2
for the next \nd2
seconds etc. We specify that w(d1) = w2(0)
,\nw(d1+d2) = w3(0)
, etc\n
\n
",
+ "meta": "func"
+ },
+ "constrain_color": {
+ "title": "constrain_color(val) \u2192 {Number}",
+ "description": "constrain_color(val) → {Number}
\n Constrains a given color value to lie between 0 and 255\n
\n
",
+ "meta": "func"
+ },
+ "copy_image": {
+ "title": "copy_image(Image, Image) \u2192 {undefined}",
+ "description": "copy_image(Image, Image) → {undefined}
\n Filter that copies all Pixels faithfully from the\nsource Image to the destination Image\n
\n
",
+ "meta": "func"
+ },
+ "copy_pixel": {
+ "title": "copy_pixel(Pixel, Pixel) \u2192 {undefined}",
+ "description": "copy_pixel(Pixel, Pixel) → {undefined}
\n Copies the red, green and blue components of a Pixel \nsrc
to a Pixel dst
\n
\n
",
+ "meta": "func"
+ },
+ "draw_connected": {
+ "title": "draw_connected(num) \u2192 {function}",
+ "description": "draw_connected(num) → {function}
\n returns a function that turns a given Curve into a Drawing, \nby sampling the Curve at num
sample points \nand connecting each pair with a line. \nWhen a program evaluates to a Drawing, the Source system\ndisplays it graphically, in a window, instead of textually.\nThe parts between (0,0) and (1,1) of the resulting Drawing \nare shown in the window.\n
\n
",
+ "meta": "func"
+ },
+ "draw_connected_full_view": {
+ "title": "draw_connected_full_view(num) \u2192 {function}",
+ "description": "draw_connected_full_view(num) → {function}
\n returns a function that turns a given Curve into a Drawing, \nby sampling the Curve at num
sample points \nand connecting each pair with a line. \nWhen a program evaluates to a Drawing, the Source system\ndisplays it graphically, in a window, instead of textually.\nThe Drawing is stretched or shrunk\nto show the full curve\nand maximize its width and height, with some padding.\n
\n
",
+ "meta": "func"
+ },
+ "draw_connected_full_view_proportional": {
+ "title": "draw_connected_full_view_proportional(num) \u2192 {function}",
+ "description": "draw_connected_full_view_proportional(num) → {function}
\n returns a function that turns a given Curve into a Drawing, \nby sampling the Curve at num
sample points \nand connecting each pair with a line. \nWhen a program evaluates to a Drawing, the Source system\ndisplays it graphically, in a window, instead of textually.\nThe Drawing is scaled proportionally to show the full curve\nand maximize its size, with some padding.\n
\n
",
+ "meta": "func"
+ },
+ "draw_connected_squeezed_to_window": {
+ "title": "draw_connected_squeezed_to_window(num) \u2192 {function}",
+ "description": "draw_connected_squeezed_to_window(num) → {function}
\n returns a function that turns a given Curve into a Drawing, \nby sampling the Curve at num
sample points \nand connecting each pair with a line. \nWhen a program evaluates to a Drawing, the Source system\ndisplays it graphically, in a window, instead of textually.\nThe Drawing is resized proportionally such that it \nis shown as big as possible, and still fits entirely \ninside the window.\n
\n
",
+ "meta": "func"
+ },
+ "draw_points_on": {
+ "title": "draw_points_on(num) \u2192 {function}",
+ "description": "draw_points_on(num) → {function}
\n returns a function that turns a given Curve into a Drawing, \nby sampling the Curve at num
sample points.\nThe Drawing consists of isolated points, and does not connect them.\nWhen a program evaluates to a Drawing, the Source system\ndisplays it graphically, in a window, instead of textually.\nThe parts between (0,0) and (1,1) of the resulting Drawing \nare shown in the window.\n
\n
",
+ "meta": "func"
+ },
+ "draw_points_squeezed_to_window": {
+ "title": "draw_points_squeezed_to_window(num) \u2192 {function}",
+ "description": "draw_points_squeezed_to_window(num) → {function}
\n returns a function that turns a given Curve into a Drawing, \nby sampling the Curve at num
sample points.\nThe Drawing consists of isolated points, and does not connect them.\nWhen a program evaluates to a Drawing, the Source system\ndisplays it graphically, in a window, instead of textually.\nThe Drawing is squeezed such that all its parts are shown in the\nwindow.\n
\n
",
+ "meta": "func"
+ },
+ "flip_horiz": {
+ "title": "flip_horiz(rune) \u2192 {Rune}",
+ "description": "flip_horiz(rune) → {Rune}
\n makes a new Rune from a given Rune by\nflipping it around a vertical axis,\ncreating a mirror image\n
\n
",
+ "meta": "func"
+ },
+ "flip_vert": {
+ "title": "flip_vert(rune) \u2192 {Rune}",
+ "description": "flip_vert(rune) → {Rune}
\n makes a new Rune from a given Rune by\nflipping it around a horizontal axis,\nturning it upside down\n
\n
",
+ "meta": "func"
+ },
+ "get_duration": {
+ "title": "get_duration(sound) \u2192 {Number}",
+ "description": "get_duration(sound) → {Number}
\n Accesses the duration of a Sound, in seconds.\n
\n
",
+ "meta": "func"
+ },
+ "get_video_height": {
+ "title": "get_video_height() \u2192 {Number}",
+ "description": "get_video_height() → {Number}
\n Returns the current height of the output video display in\npixels, i.e. the number of pixels in vertical direction\n
\n
",
+ "meta": "func"
+ },
+ "get_video_width": {
+ "title": "get_video_width() \u2192 {Number}",
+ "description": "get_video_width() → {Number}
\n Returns the current width of the output video display in\npixels, i.e. the number of pixels in horizontal direction\n
\n
",
+ "meta": "func"
+ },
+ "get_wave": {
+ "title": "get_wave(sound) \u2192 {function}",
+ "description": "get_wave(sound) → {function}
\n Accesses the wave of a Sound.\nThe wave is a function from a non-negative time (in seconds)\nto an amplitude value that should lie between\n-1 and 1.\n
\n
",
+ "meta": "func"
+ },
+ "gosper_curve": {
+ "title": "gosper_curve(level) \u2192 {Curve}",
+ "description": "gosper_curve(level) → {Curve}
\n returns a gosper Curve, that results from\napply gosperize as many times to the unit line\nas given by the parameter level
of\nthe function gosper_curve
\n
\n
",
+ "meta": "func"
+ },
+ "gosperize": {
+ "title": "gosperize(curve) \u2192 {Curve}",
+ "description": "gosperize(curve) → {Curve}
\n this function is a unary Curve operator: It\ntakes a Curve as argument and returns\na new Curve, according to the Gosper operation.\n
\n
",
+ "meta": "func"
+ },
+ "green": {
+ "title": "green(rune) \u2192 {Rune}",
+ "description": "green(rune) → {Rune}
\n colors the given rune green.\n
\n
",
+ "meta": "func"
+ },
+ "green_of": {
+ "title": "green_of(Pixel) \u2192 {Number}",
+ "description": "green_of(Pixel) → {Number}
\n Returns the green component of a given Pixel px
\n
\n
",
+ "meta": "func"
+ },
+ "indigo": {
+ "title": "indigo(rune) \u2192 {Rune}",
+ "description": "indigo(rune) → {Rune}
\n colors the given rune indigo.\n
\n
",
+ "meta": "func"
+ },
+ "init_record": {
+ "title": "init_record() \u2192 {undefined}",
+ "description": "init_record() → {undefined}
\n Initialize recording by obtaining permission\nto use the default device microphone\n
\n
",
+ "meta": "func"
+ },
+ "invert": {
+ "title": "invert(original) \u2192 {Curve}",
+ "description": "invert(original) → {Curve}
\n this function is a unary Curve operator: a function from a\nCurve to a Curve. The points of the result Curve are\nthe same points as the points of the original Curve, but\nin reverse: The result Curve applied to 0 is the original Curve\napplied to 1 and vice versa.\n
\n
",
+ "meta": "func"
+ },
+ "is_sound": {
+ "title": "is_sound(x) \u2192 {boolean}",
+ "description": "is_sound(x) → {boolean}
\n Checks if a given value is a Sound\n
\n
",
+ "meta": "func"
+ },
+ "letter_name_to_frequency": {
+ "title": "letter_name_to_frequency(str) \u2192 {Number}",
+ "description": "letter_name_to_frequency(str) → {Number}
\n converts a letter name str
to corresponding frequency.\nFirst converts str
to a note using letter_name_to_midi_note
\nand then to a frequency using midi_note_to_frequency
\n
\n
",
+ "meta": "func"
+ },
+ "letter_name_to_midi_note": {
+ "title": "letter_name_to_midi_note(str) \u2192 {Number}",
+ "description": "letter_name_to_midi_note(str) → {Number}
\n
",
+ "meta": "func"
+ },
+ "make_cross": {
+ "title": "make_cross(rune) \u2192 {Rune}",
+ "description": "make_cross(rune) → {Rune}
\n makes a new Rune from a given Rune by\narranging into a square for copies of the \ngiven Rune in different orientations\n
\n
",
+ "meta": "func"
+ },
+ "make_point": {
+ "title": "make_point(x, y) \u2192 {Point}",
+ "description": "make_point(x, y) → {Point}
\n makes a Point with given x and y coordinates\n
\n
",
+ "meta": "func"
+ },
+ "make_sound": {
+ "title": "make_sound(wave, duration) \u2192 {Sound}",
+ "description": "make_sound(wave, duration) → {Sound}
\n Makes a Sound from a wave and a duration.\nThe wave is a function from a non-negative time (in seconds)\nto an amplitude value that should lie between\n-1 and 1. The duration is given in seconds.\n
\n
",
+ "meta": "func"
+ },
+ "midi_note_to_frequency": {
+ "title": "midi_note_to_frequency(n) \u2192 {Number}",
+ "description": "midi_note_to_frequency(n) → {Number}
\n converts a midi note n
to corresponding frequency.\nThe note is given as an integer Number.\n
\n
",
+ "meta": "func"
+ },
+ "noise_sound": {
+ "title": "noise_sound(duration) \u2192 {Sound}",
+ "description": "noise_sound(duration) → {Sound}
\n makes a Sound of a given duration by randomly\ngenerating amplitude values\n
\n
",
+ "meta": "func"
+ },
+ "orange": {
+ "title": "orange(rune) \u2192 {Rune}",
+ "description": "orange(rune) → {Rune}
\n colors the given rune orange.\n
\n
",
+ "meta": "func"
+ },
+ "overlay": {
+ "title": "overlay(rune1, rune2) \u2192 {Rune}",
+ "description": "overlay(rune1, rune2) → {Rune}
\n makes a 3D-Rune from two given Runes by\noverlaying the first with the second, each\noccupying equal parts of the depth of the\nresult\n
\n
",
+ "meta": "func"
+ },
+ "overlay_frac": {
+ "title": "overlay_frac(frac, rune1, rune2) \u2192 {Rune}",
+ "description": "overlay_frac(frac, rune1, rune2) → {Rune}
\n makes a 3D-Rune from two given Runes by\noverlaying the first with the second\nsuch that the first one occupies frac \nportion of the depth of the 3D result \nand the second the rest\n
\n
",
+ "meta": "func"
+ },
+ "param_gosper": {
+ "title": "param_gosper(level, angle_at) \u2192 {Curve}",
+ "description": "param_gosper(level, angle_at) → {Curve}
\n returns a Curve that results from gosperizing the unit line\nas often as given by the level parameter, each time\napplying an angle given by the given angle-producing function\n
\n
",
+ "meta": "func"
+ },
+ "param_gosperize": {
+ "title": "param_gosperize(curve) \u2192 {Curve}",
+ "description": "param_gosperize(curve) → {Curve}
\n this function takes an angle theta and returns a unary Curve operator:\nA function that takes a Curve as argument and returns\na new Curve, according to the Gosper operation, modified\nwith the given angle theta\n
\n
",
+ "meta": "func"
+ },
+ "piano": {
+ "title": "piano(note, duration) \u2192 {Sound}",
+ "description": "piano(note, duration) → {Sound}
\n returns a Sound that is reminiscent of a piano, playing\na given note for a given duration
of seconds\n
\n
",
+ "meta": "func"
+ },
+ "pink": {
+ "title": "pink(rune) \u2192 {Rune}",
+ "description": "pink(rune) → {Rune}
\n colors the given rune pink.\n
\n
",
+ "meta": "func"
+ },
+ "play": {
+ "title": "play(sound) \u2192 {Sound}",
+ "description": "play(sound) → {Sound}
\n plays a given Sound using your computer's sound device\n
\n
",
+ "meta": "func"
+ },
+ "play_concurrently": {
+ "title": "play_concurrently(sound) \u2192 {undefined}",
+ "description": "play_concurrently(sound) → {undefined}
\n plays a given sound without regard if a sound is already playing\n
\n
",
+ "meta": "func"
+ },
+ "purple": {
+ "title": "purple(rune) \u2192 {Rune}",
+ "description": "purple(rune) → {Rune}
\n colors the given rune purple.\n
\n
",
+ "meta": "func"
+ },
+ "put_in_standard_position": {
+ "title": "put_in_standard_position(curve) \u2192 {Curve}",
+ "description": "put_in_standard_position(curve) → {Curve}
\n this function is a unary Curve operator: It\ntakes a Curve as argument and returns\na new Curve, as follows.\nA Curve is in standard position if it starts at (0,0) ends at (1,0).\nThis function puts the given Curve in standard position by \nrigidly translating it so its\nstart Point is at the origin (0,0), then rotating it about the origin to put\nits endpoint on the x axis, then scaling it to put the endpoint at (1,0).\nBehavior is unspecified on closed Curves where start-point equal end-point.\n
\n
",
+ "meta": "func"
+ },
+ "quarter_turn_left": {
+ "title": "quarter_turn_left(rune) \u2192 {Rune}",
+ "description": "quarter_turn_left(rune) → {Rune}
\n makes a new Rune from a given Rune\nby turning it a quarter-turn in\nanti-clockwise direction.\n
\n
",
+ "meta": "func"
+ },
+ "quarter_turn_right": {
+ "title": "quarter_turn_right(rune) \u2192 {Rune}",
+ "description": "quarter_turn_right(rune) → {Rune}
\n makes a new Rune from a given Rune\nby turning it a quarter-turn around the centre in\nclockwise direction.\n
\n
",
+ "meta": "func"
+ },
+ "random_color": {
+ "title": "random_color(rune) \u2192 {Rune}",
+ "description": "random_color(rune) → {Rune}
\n Gives random color to the given rune.\nThe color is chosen randomly from the following nine \ncolors: red, pink, purple, indigo, blue, green, yellow, orange, brown\n
\n
",
+ "meta": "func"
+ },
+ "record": {
+ "title": "record(buffer) \u2192 {function}",
+ "description": "record(buffer) → {function}
\n takes a
buffer
duration (in seconds) as argument, and\nreturns a nullary stop function
stop
. A call\n
stop()
returns a sound promise: a nullary function\nthat returns a sound. Example:
init_record();\nconst stop = record(0.5);\n// record after 0.5 seconds. Then in next query:\nconst promise = stop();\n// In next query, you can play the promised sound, by\n// applying the promise:\nplay(promise());
\n
\n
",
+ "meta": "func"
+ },
+ "record_for": {
+ "title": "record_for(duration, buffer) \u2192 {function}",
+ "description": "record_for(duration, buffer) → {function}
\n Records a sound of given
duration
in seconds, after\na
buffer
also in seconds, and\nreturns a sound promise: a nullary function\nthat returns a sound. Example:
init_record();\nconst promise = record_for(2, 0.5);\n// In next query, you can play the promised sound, by\n// applying the promise:\nplay(promise());
\n
\n
",
+ "meta": "func"
+ },
+ "red": {
+ "title": "red(rune) \u2192 {Rune}",
+ "description": "red(rune) → {Rune}
\n colors the given rune red.\n
\n
",
+ "meta": "func"
+ },
+ "red_of": {
+ "title": "red_of(Pixel) \u2192 {Number}",
+ "description": "red_of(Pixel) → {Number}
\n Returns the red component of a given Pixel px
\n
\n
",
+ "meta": "func"
+ },
+ "repeat_pattern": {
+ "title": "repeat_pattern(n, f, initial) \u2192 {t}",
+ "description": "repeat_pattern(n, f, initial) → {t}
\n applies a given function n times to an initial value\n
\n
",
+ "meta": "func"
+ },
+ "rotate": {
+ "title": "rotate(rad, rune) \u2192 {Rune}",
+ "description": "rotate(rad, rune) → {Rune}
\n rotates a given Rune by a given angle,\ngiven in radians, in anti-clockwise direction.\nNote that parts of the Rune\nmay be cropped as a result.\n
\n
",
+ "meta": "func"
+ },
+ "rotate_around_origin": {
+ "title": "rotate_around_origin(theta) \u2192 {unary_Curve_operator}",
+ "description": "rotate_around_origin(theta) → {unary_Curve_operator}
\n this function \ntakes an angle theta as parameter and returns a unary Curve operator:\na function that takes\na Curve a argument and returns\na new Curve, which is the original Curve rotated by the given angle\naround the origin, in counter-clockwise direction.\n
\n
",
+ "meta": "func"
+ },
+ "rotate_pi_over_2": {
+ "title": "rotate_pi_over_2(original) \u2192 {Curve}",
+ "description": "rotate_pi_over_2(original) → {Curve}
\n this function is a unary Curve operator: a function from a\nCurve to a Curve. The result Curve is the original Curve\nrotated by 90 degrees in counterclockwise direction around\nthe origin.\n
\n
",
+ "meta": "func"
+ },
+ "sawtooth_sound": {
+ "title": "sawtooth_sound(freq, duration) \u2192 {Sound}",
+ "description": "sawtooth_sound(freq, duration) → {Sound}
\n makes a sawtooth wave Sound with given frequency and a given duration\n
\n
",
+ "meta": "func"
+ },
+ "scale": {
+ "title": "scale(s) \u2192 {unary_Curve_operator}",
+ "description": "scale(s) → {unary_Curve_operator}
\n this function takes a scaling factor s argument and returns a\nunary Curve operator that\nscales a given Curve by s in x and y direction.\n
\n
",
+ "meta": "func"
+ },
+ "scale_independent": {
+ "title": "scale_independent(ratio_x, ratio_y, rune) \u2192 {Rune}",
+ "description": "scale_independent(ratio_x, ratio_y, rune) → {Rune}
\n scales a given Rune by separate factors in x and y direction\n
\n
",
+ "meta": "func"
+ },
+ "scale_x_y": {
+ "title": "scale_x_y(a, b) \u2192 {unary_Curve_operator}",
+ "description": "scale_x_y(a, b) → {unary_Curve_operator}
\n this function takes scaling factors a
and b
as arguments \nand returns a unary Curve operator that\nscales a given Curve by a
in x-direction and by b
\nin y-direction.\n
\n
",
+ "meta": "func"
+ },
+ "set_rgb": {
+ "title": "set_rgb(Pixel, Number, Number, Number, Pixel) \u2192 {undefined}",
+ "description": "set_rgb(Pixel, Number, Number, Number, Pixel) → {undefined}
\n Assigns the red, green and blue components of a pixel \npx
to given values\n
\n
",
+ "meta": "func"
+ },
+ "show": {
+ "title": "show(rune) \u2192 {Picture}",
+ "description": "show(rune) → {Picture}
\n turns a given Rune into a two-dimensional Picture\n
\n
",
+ "meta": "func"
+ },
+ "show_connected_gosper": {
+ "title": "show_connected_gosper(level) \u2192 {Drawing}",
+ "description": "show_connected_gosper(level) → {Drawing}
\n shows a gosper Curve of given level, by drawing it\nwith suitable parameters\n
\n
",
+ "meta": "func"
+ },
+ "silence_sound": {
+ "title": "silence_sound(duration) \u2192 {Sound}",
+ "description": "silence_sound(duration) → {Sound}
\n makes a silence Sound with a given duration\n
\n
",
+ "meta": "func"
+ },
+ "simultaneously": {
+ "title": "simultaneously(sounds) \u2192 {Sound}",
+ "description": "simultaneously(sounds) → {Sound}
\n makes a new sound by combining the sounds in a given\nlist so that\nthey play simutaneously, all starting at the beginning of the \nresulting sound\n
\n
",
+ "meta": "func"
+ },
+ "sine_sound": {
+ "title": "sine_sound(freq, duration) \u2192 {Sound}",
+ "description": "sine_sound(freq, duration) → {Sound}
\n makes a sine wave Sound with given frequency and a given duration\n
\n
",
+ "meta": "func"
+ },
+ "square_sound": {
+ "title": "square_sound(freq, duration) \u2192 {Sound}",
+ "description": "square_sound(freq, duration) → {Sound}
\n makes a square wave Sound with given frequency and a given duration\n
\n
",
+ "meta": "func"
+ },
+ "stack": {
+ "title": "stack(rune1, rune2) \u2192 {Rune}",
+ "description": "stack(rune1, rune2) → {Rune}
\n makes a new Rune from two given Runes by\nplacing the first on top of the second, each\noccupying equal parts of the height of the \nresult\n
\n
",
+ "meta": "func"
+ },
+ "stack_frac": {
+ "title": "stack_frac(frac, rune1, rune2) \u2192 {Rune}",
+ "description": "stack_frac(frac, rune1, rune2) → {Rune}
\n makes a new Rune from two given Runes by\nplacing the first on top of the second\nsuch that the first one occupies frac \nportion of the height of the result and \nthe second the rest\n
\n
",
+ "meta": "func"
+ },
+ "stacking_adsr": {
+ "title": "stacking_adsr(waveform, base_frequency, duration, envelopes) \u2192 {Sound}",
+ "description": "stacking_adsr(waveform, base_frequency, duration, envelopes) → {Sound}
\n Returns a Sound that results from applying a list of envelopes\nto a given wave form. The wave form should be a Sound generator that\ntakes a frequency and a duration as arguments and produces a\nSound with the given frequency and duration. Each envelope is\napplied to a harmonic: the first harmonic has the given frequency,\nthe second has twice the frequency, the third three times the\nfrequency etc.\n
\n
",
+ "meta": "func"
+ },
+ "stackn": {
+ "title": "stackn(n, rune) \u2192 {Rune}",
+ "description": "stackn(n, rune) → {Rune}
\n makes a new Rune from a given Rune\nby vertically stacking n copies of it\n
\n
",
+ "meta": "func"
+ },
+ "stop": {
+ "title": "stop() \u2192 {undefined}",
+ "description": "stop() → {undefined}
\n Stops playing the current sound\n
\n
",
+ "meta": "func"
+ },
+ "translate": {
+ "title": "translate(x0, y0) \u2192 {function}",
+ "description": "translate(x0, y0) → {function}
\n this function returns a unary Curve operator: \nIt takes an x-value x0 and a y-value y0 as arguments and returns a\nunary Curve operator that\ntakes a Curve as argument and returns\na new Curve, by translating the original by x0 in x-direction\nand by y0 in y-direction.\n
\n
",
+ "meta": "func"
+ },
+ "triangle_sound": {
+ "title": "triangle_sound(freq, duration) \u2192 {Sound}",
+ "description": "triangle_sound(freq, duration) → {Sound}
\n makes a triangle wave Sound with given frequency and a given duration\n
\n
",
+ "meta": "func"
+ },
+ "trombone": {
+ "title": "trombone(note, duration) \u2192 {Sound}",
+ "description": "trombone(note, duration) → {Sound}
\n returns a Sound that is reminiscent of a trombone, playing\na given note for a given duration
of seconds\n
\n
",
+ "meta": "func"
+ },
+ "turn_upside_down": {
+ "title": "turn_upside_down(rune) \u2192 {Rune}",
+ "description": "turn_upside_down(rune) → {Rune}
\n makes a new Rune from a given Rune\nby turning it upside-down\n
\n
",
+ "meta": "func"
+ },
+ "unit_circle": {
+ "title": "unit_circle(t) \u2192 {Point}",
+ "description": "unit_circle(t) → {Point}
\n this function is a curve: a function from a\nfraction t to a point. The points lie on the\nunit circle. They start at Point (1,0) when\nt is 0. When t is 0.25, they reach Point (0,1),\nwhen t is 0.5, they reach Point (-1, 0), etc.\n
\n
",
+ "meta": "func"
+ },
+ "unit_line": {
+ "title": "unit_line(t) \u2192 {Point}",
+ "description": "unit_line(t) → {Point}
\n this function is a curve: a function from a\nfraction t to a point. The x-coordinate at\nfranction t is t, and the y-coordinate is 0.\n
\n
",
+ "meta": "func"
+ },
+ "unit_line_at": {
+ "title": "unit_line_at(t) \u2192 {Curve}",
+ "description": "unit_line_at(t) → {Curve}
\n this function is a Curve generator: it takes\na number and returns a horizontal curve. The number\nis a y-coordinate, and the Curve generates\nonly points with the given y-coordinate.\n
\n
",
+ "meta": "func"
+ },
+ "violin": {
+ "title": "violin(note, duration) \u2192 {Sound}",
+ "description": "violin(note, duration) → {Sound}
\n returns a Sound that is reminiscent of a violin, playing\na given note for a given duration
of seconds\n
\n
",
+ "meta": "func"
+ },
+ "white": {
+ "title": "white(rune) \u2192 {Rune}",
+ "description": "white(rune) → {Rune}
\n colors the given rune white.\n
\n
",
+ "meta": "func"
+ },
+ "x_of": {
+ "title": "x_of(p) \u2192 {Number}",
+ "description": "x_of(p) → {Number}
\n retrieves the x-coordinate a given Point\n
\n
",
+ "meta": "func"
+ },
+ "y_of": {
+ "title": "y_of(p) \u2192 {Number}",
+ "description": "y_of(p) → {Number}
\n retrieves the y-coordinate a given Point\n
\n
",
+ "meta": "func"
+ },
+ "yellow": {
+ "title": "yellow(rune) \u2192 {Rune}",
+ "description": "yellow(rune) → {Rune}
\n colors the given rune yellow.\n
\n
",
+ "meta": "func"
+ }
+}
\ No newline at end of file
diff --git a/src/editors/ace/docTooltip/index.ts b/src/editors/ace/docTooltip/index.ts
new file mode 100644
index 000000000..a09e15544
--- /dev/null
+++ b/src/editors/ace/docTooltip/index.ts
@@ -0,0 +1,17 @@
+import * as ext_lib from './External libraries.json'
+import * as source_1 from './source_1.json'
+import * as source_2 from './source_2.json'
+import * as source_3 from './source_3.json'
+import * as source_3_concurrent from './source_3_concurrent.json'
+import * as source_4 from './source_4.json'
+
+export const SourceDocumentation = {
+ builtins: {
+ '1': source_1,
+ '2': source_2,
+ '3': source_3,
+ '3_concurrent': source_3_concurrent,
+ '4': source_4
+ },
+ ext_lib
+}
diff --git a/src/editors/ace/docTooltip/source_1.json b/src/editors/ace/docTooltip/source_1.json
new file mode 100644
index 000000000..68aeec9e6
--- /dev/null
+++ b/src/editors/ace/docTooltip/source_1.json
@@ -0,0 +1,282 @@
+{
+ "Infinity": {
+ "title": "Infinity:number",
+ "description": "",
+ "meta": "const"
+ },
+ "math_LN2": {
+ "title": "math_LN2:number",
+ "description": "math_LN2:number
\n The Number value for the natural logarithm of 2, \nwhich is approximately 0.6931471805599453.\n
\n
",
+ "meta": "const"
+ },
+ "math_LN10": {
+ "title": "math_LN10:number",
+ "description": "math_LN10:number
\n The Number value for the natural logarithm of 10, \nwhich is approximately 2.302585092994046.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG2E": {
+ "title": "math_LOG2E:number",
+ "description": "math_LOG2E:number
\n The Number value for the base-2 logarithm of eℝ, the base of the natural logarithms; \nthis value is approximately 1.4426950408889634.\n
NOTE:\nThe value of math_LOG2E is approximately the reciprocal of the value of math_LN2.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG10E": {
+ "title": "math_LOG10E:number",
+ "description": "math_LOG10E:number
\n The Number value for the base-10 logarithm of e, \nthe base of the natural logarithms; this value is approximately 0.4342944819032518.\n
NOTE:\nThe value of math_LOG10E is approximately the reciprocal of the value of math_LN10.\n
\n
",
+ "meta": "const"
+ },
+ "math_PI": {
+ "title": "math_PI:number",
+ "description": "math_PI:number
\n The Number value for π, the ratio of the circumference of a circle to its diameter, \nwhich is approximately 3.1415926535897932.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT1_2": {
+ "title": "math_SQRT1_2:number",
+ "description": "math_SQRT1_2:number
\n The Number value for the square root of 0.5, which is approximately 0.7071067811865476.\n
NOTE:\nThe value of math_SQRT1_2 is approximately the reciprocal of the value of math_SQRT2.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT2": {
+ "title": "math_SQRT2:number",
+ "description": "math_SQRT2:number
\n The Number value for the square root of 2, which is approximately 1.4142135623730951.\n
\n
",
+ "meta": "const"
+ },
+ "NaN": {
+ "title": "NaN:number",
+ "description": "",
+ "meta": "const"
+ },
+ "undefined": {
+ "title": "undefined:undefined",
+ "description": "",
+ "meta": "const"
+ },
+ "display": {
+ "title": "display(v, s) \u2192 {value}",
+ "description": "display(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console. The notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "error": {
+ "title": "error(v, s) \u2192 {value}",
+ "description": "error(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console with error flag. \nThe evaluation\nof any call of
error
aborts the running program immediately.\nThe notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "is_boolean": {
+ "title": "is_boolean(v) \u2192 {boolean}",
+ "description": "is_boolean(v) → {boolean}
\n checks whether a given value is a boolean\n
\n
",
+ "meta": "func"
+ },
+ "is_function": {
+ "title": "is_function(v) \u2192 {boolean}",
+ "description": "is_function(v) → {boolean}
\n checks whether a given value is a function\n
\n
",
+ "meta": "func"
+ },
+ "is_number": {
+ "title": "is_number(v) \u2192 {boolean}",
+ "description": "is_number(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_string": {
+ "title": "is_string(v) \u2192 {boolean}",
+ "description": "is_string(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_undefined": {
+ "title": "is_undefined(v) \u2192 {boolean}",
+ "description": "is_undefined(v) → {boolean}
\n checks whether a given value is the special value undefined
\n
\n
",
+ "meta": "func"
+ },
+ "math_abs": {
+ "title": "math_abs(x) \u2192 {number}",
+ "description": "math_abs(x) → {number}
\n computes the absolute value of x; the result has the same magnitude as x
but has positive sign.\n
\n
",
+ "meta": "func"
+ },
+ "math_acos": {
+ "title": "math_acos(x) \u2192 {number}",
+ "description": "math_acos(x) → {number}
\n computes the arc cosine of x
. \nThe result is expressed in radians and ranges from +0 to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_acosh": {
+ "title": "math_acosh(x) \u2192 {number}",
+ "description": "math_acosh(x) → {number}
\n computes the inverse hyperbolic cosine of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_asin": {
+ "title": "math_asin(x) \u2192 {number}",
+ "description": "math_asin(x) → {number}
\n computes the arc sine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_asinh": {
+ "title": "math_asinh(x) \u2192 {number}",
+ "description": "math_asinh(x) → {number}
\n computes the inverse hyperbolic \nsine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan": {
+ "title": "math_atan(x) \u2192 {number}",
+ "description": "math_atan(x) → {number}
\n computes the arc tangent of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan2": {
+ "title": "math_atan2(y, x) \u2192 {number}",
+ "description": "math_atan2(y, x) → {number}
\n computes the arc tangent of the quotient y
/ x
of the arguments y
and x
, where the signs of y
and x
are used to determine the quadrant of the result. Note that it is intentional and traditional for the two-argument arc tangent function that the argument named y
be first and the argument named x
be second. The result is expressed in radians and ranges from -π to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_atanh": {
+ "title": "math_atanh(x) \u2192 {number}",
+ "description": "math_atanh(x) → {number}
\n computes the inverse hyperbolic tangent of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_cbrt": {
+ "title": "math_cbrt(x) \u2192 {number}",
+ "description": "math_cbrt(x) → {number}
\n computes the cube root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_ceil": {
+ "title": "math_ceil(x) \u2192 {number}",
+ "description": "math_ceil(x) → {number}
\n computes the smallest (closest to -∞) Number value that is not less than x
and is an integer. If x
is already an integer, the result is x
.\nThe value of math_ceil(x) is the same as the value of -math_floor(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_clz32": {
+ "title": "math_clz32(n) \u2192 {number}",
+ "description": "math_clz32(n) → {number}
\n When math_clz32 is called with one argument
x
, the following steps are taken:\nLet n be ToUint32(x).\nLet p be the number of leading zero bits in the 32-bit binary representation of n.\nReturn p.\n
NOTE:\n
If n is 0, p will be 32. If the most significant bit of the 32-bit binary encoding of n is 1, \np will be 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_cos": {
+ "title": "math_cos(x) \u2192 {number}",
+ "description": "math_cos(x) → {number}
\n Computes the cosine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_cosh": {
+ "title": "math_cosh(x) \u2192 {number}",
+ "description": "math_cosh(x) → {number}
\n computes the hyperbolic cosine of
x
.\n
NOTE:\nThe value of cosh(x) is the same as (exp(x) + exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_exp": {
+ "title": "math_exp(x) \u2192 {number}",
+ "description": "math_exp(x) → {number}
\n computes the exponential function of x
\n(e raised to the power of x
, where e is the base of the natural logarithms).\n
\n
",
+ "meta": "func"
+ },
+ "math_expm1": {
+ "title": "math_expm1(x) \u2192 {number}",
+ "description": "math_expm1(x) → {number}
\n computes subtracting 1 from the \nexponential function of x
(e raised to the power of x
, where e is the base of \nthe natural logarithms). The result is computed in a way that is accurate even \nwhen the value of x
is close 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_floor": {
+ "title": "math_floor(x) \u2192 {number}",
+ "description": "math_floor(x) → {number}
\n computes the greatest (closest to +∞) Number value that is not greater than
x
\nand is an integer. \n
If
x
is already an integer, the result is
x
.\n
NOTE:\nThe value of math_floor(x) is the same as the value of -math_ceil(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_fround": {
+ "title": "math_fround(x) \u2192 {number}",
+ "description": "math_fround(x) → {number}
\n When math_fround is called with argument
x
, the following steps are taken:\n
- If
x
is NaN, return NaN. \n- If
x
is one of +0, -0, +∞, -∞, return x
. \n- Let x32 be the result of converting
x
to a value in IEEE 754-2008 binary32 format using roundTiesToEven mode. \n- Let x64 be the result of converting x32 to a value in IEEE 754-2008 binary64 format.
\n- Return the ECMAScript Number value corresponding to x64.
\n
\n
",
+ "meta": "func"
+ },
+ "math_hypot": {
+ "title": "math_hypot() \u2192 {number}",
+ "description": "math_hypot() → {number}
\n computes the square root\nof the sum of squares of its arguments.\n
If no arguments are passed, the result is +0.\n
\n
",
+ "meta": "func"
+ },
+ "math_imul": {
+ "title": "math_imul(x, x) \u2192 {number}",
+ "description": "math_imul(x, x) → {number}
\n When math_imul is called with arguments
x
and
y
,\nthe following steps are taken:\n
\n- Let a be ToUint32(x).
\n- Let b be ToUint32(y).
\n- Let product be (a × b) modulo 232.
\n- If product ≥ 231, return product - 232; otherwise return product.
\n
\n
",
+ "meta": "func"
+ },
+ "math_log": {
+ "title": "math_log(x) \u2192 {number}",
+ "description": "math_log(x) → {number}
\n Computes the natural logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log1p": {
+ "title": "math_log1p(x) \u2192 {number}",
+ "description": "math_log1p(x) → {number}
\n computes the natural logarithm of 1 + x
. The result is computed in a way that is accurate even when the value of x
is close to zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_log2": {
+ "title": "math_log2(x) \u2192 {number}",
+ "description": "math_log2(x) → {number}
\n computes the base 2 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log10": {
+ "title": "math_log10(x) \u2192 {number}",
+ "description": "math_log10(x) → {number}
\n computes the base 10 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_max": {
+ "title": "math_max() \u2192 {number}",
+ "description": "math_max() → {number}
\n Given zero or more numbers, returns the largest of them.\n
If no arguments are given, the result is -∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the largest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_min": {
+ "title": "math_min() \u2192 {number}",
+ "description": "math_min() → {number}
\n Given zero or more arguments, returns the smallest of them.\n
If no arguments are given, the result is +∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the smallest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_pow": {
+ "title": "math_pow(base, exponent) \u2192 {number}",
+ "description": "math_pow(base, exponent) → {number}
\n Computes the result of raising base to \nthe power of exponent.\n
\n
",
+ "meta": "func"
+ },
+ "math_random": {
+ "title": "math_random() \u2192 {number}",
+ "description": "math_random() → {number}
\n Returns a number value with positive sign, greater than or equal to 0 but less than 1, \nchosen randomly or pseudo randomly with approximately uniform distribution over that \nrange, using an implementation-dependent algorithm or strategy. This function takes no arguments.\nEach math_random function created for distinct realms must produce a distinct sequence \nof values from successive calls.\n
\n
",
+ "meta": "func"
+ },
+ "math_round": {
+ "title": "math_round(x) \u2192 {number}",
+ "description": "math_round(x) → {number}
\n Returns the number value that is closest to x
and is an integer. \n
If two integers are equally close to x
, then the result is the Number value \nthat is closer to +∞. If x
is already an integer, the result is x
.\nNOTE 1:\nmath_round(3.5) returns 4, but math_round(-3.5) returns -3.\n
\n
",
+ "meta": "func"
+ },
+ "math_sign": {
+ "title": "math_sign(x) \u2192 {number}",
+ "description": "math_sign(x) → {number}
\n Computes the sign of x
, indicating whether x
is positive, negative, or zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_sin": {
+ "title": "math_sin(x) \u2192 {number}",
+ "description": "math_sin(x) → {number}
\n Computes the sine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_sinh": {
+ "title": "math_sinh(x) \u2192 {number}",
+ "description": "math_sinh(x) → {number}
\n Computes the hyperbolic sine of
x
.\n
NOTE:\nThe value of sinh(x) is the same as (exp(x) - exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_sqrt": {
+ "title": "math_sqrt(x) \u2192 {number}",
+ "description": "math_sqrt(x) → {number}
\n Computes the square root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_tan": {
+ "title": "math_tan(x) \u2192 {number}",
+ "description": "math_tan(x) → {number}
\n Computes the tangent of x
. The argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_tanh": {
+ "title": "math_tanh(x) \u2192 {number}",
+ "description": "math_tanh(x) → {number}
\n Computes the hyperbolic tangent of
x
.\n
NOTE:\nThe value of
math_tanh(x)
is the same as\n
(exp(x) - exp(-x))/(exp(x) + exp(-x))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_trunc": {
+ "title": "math_trunc(x) \u2192 {number}",
+ "description": "math_trunc(x) → {number}
\n Computes the integral part of the number x
,\nremoving any fractional digits.\n
\n
",
+ "meta": "func"
+ },
+ "parse_int": {
+ "title": "parse_int(s, i) \u2192 {number}",
+ "description": "parse_int(s, i) → {number}
\n Interprets a given string
s
as an integer, \nusing the positive integer
i
as radix, \nand returns the respective value.\n
Examples:
parse_int(\"909\", 10)
returns the number \n
909
, and
parse_int(\"-1111\", 2)
returns the number \n
-15
.
\nSee
ECMAScript Specification, Section 18.2.5 for details.\n
\n
",
+ "meta": "func"
+ },
+ "prompt": {
+ "title": "prompt(s) \u2192 {string}",
+ "description": "prompt(s) → {string}
\n Pops up a window that displays the string s
, provides\nan input line for the user to enter a text, a Cancel
button and an OK
button. \nThe call of prompt
\nsuspends execution of the program until one of the two buttons is pressed. If \nthe OK
button is pressed, prompt
returns the entered text as a string.\nIf the Cancel
button is pressed, prompt
returns a non-string value.\n
\n
",
+ "meta": "func"
+ },
+ "runtime": {
+ "title": "runtime() \u2192 {number}",
+ "description": "runtime() → {number}
\n Returns number of milliseconds elapsed since January 1, 1970 00:00:00 UTC.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "stringify": {
+ "title": "stringify(v) \u2192 {string}",
+ "description": "stringify(v) → {string}
\n returns a string that represents the value
v
, using a\nnotation that is is consistent with \n
JSON, \nbut also displays
undefined
and function objects.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ }
+}
\ No newline at end of file
diff --git a/src/editors/ace/docTooltip/source_2.json b/src/editors/ace/docTooltip/source_2.json
new file mode 100644
index 000000000..37568b24f
--- /dev/null
+++ b/src/editors/ace/docTooltip/source_2.json
@@ -0,0 +1,397 @@
+{
+ "Infinity": {
+ "title": "Infinity:number",
+ "description": "",
+ "meta": "const"
+ },
+ "math_LN2": {
+ "title": "math_LN2:number",
+ "description": "math_LN2:number
\n The Number value for the natural logarithm of 2, \nwhich is approximately 0.6931471805599453.\n
\n
",
+ "meta": "const"
+ },
+ "math_LN10": {
+ "title": "math_LN10:number",
+ "description": "math_LN10:number
\n The Number value for the natural logarithm of 10, \nwhich is approximately 2.302585092994046.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG2E": {
+ "title": "math_LOG2E:number",
+ "description": "math_LOG2E:number
\n The Number value for the base-2 logarithm of eℝ, the base of the natural logarithms; \nthis value is approximately 1.4426950408889634.\n
NOTE:\nThe value of math_LOG2E is approximately the reciprocal of the value of math_LN2.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG10E": {
+ "title": "math_LOG10E:number",
+ "description": "math_LOG10E:number
\n The Number value for the base-10 logarithm of e, \nthe base of the natural logarithms; this value is approximately 0.4342944819032518.\n
NOTE:\nThe value of math_LOG10E is approximately the reciprocal of the value of math_LN10.\n
\n
",
+ "meta": "const"
+ },
+ "math_PI": {
+ "title": "math_PI:number",
+ "description": "math_PI:number
\n The Number value for π, the ratio of the circumference of a circle to its diameter, \nwhich is approximately 3.1415926535897932.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT1_2": {
+ "title": "math_SQRT1_2:number",
+ "description": "math_SQRT1_2:number
\n The Number value for the square root of 0.5, which is approximately 0.7071067811865476.\n
NOTE:\nThe value of math_SQRT1_2 is approximately the reciprocal of the value of math_SQRT2.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT2": {
+ "title": "math_SQRT2:number",
+ "description": "math_SQRT2:number
\n The Number value for the square root of 2, which is approximately 1.4142135623730951.\n
\n
",
+ "meta": "const"
+ },
+ "NaN": {
+ "title": "NaN:number",
+ "description": "",
+ "meta": "const"
+ },
+ "undefined": {
+ "title": "undefined:undefined",
+ "description": "",
+ "meta": "const"
+ },
+ "accumulate": {
+ "title": "accumulate(f, initial, xs) \u2192 {value}",
+ "description": "accumulate(f, initial, xs) → {value}
\n Applies binary\nfunction f
to the elements of xs
from\nright-to-left order, first applying f
to the last element\nand the value initial
, resulting in r
1,\nthen to the \nsecond-last element and r
1, resulting in\nr
2,\netc, and finally\nto the first element and r
n-1, where\nn
is the length of the\nlist. Thus, accumulate(f,zero,list(1,2,3))
results in\nf(1, f(2, f(3, zero)))
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
\nassuming f
takes constant time.\n
\n
",
+ "meta": "func"
+ },
+ "append": {
+ "title": "append(xs, ys) \u2192 {list}",
+ "description": "append(xs, ys) → {list}
\n Returns a list that results from \nappending the list ys
to the list xs
.\nRecursive process; time: O(n)
, space:\nO(n)
, where n
is the length of xs
.\nIn the result, null at the end of the first argument list\nis replaced by the second argument, regardless what the second\nargument consists of.\n
\n
",
+ "meta": "func"
+ },
+ "build_list": {
+ "title": "build_list(n, f) \u2192 {list}",
+ "description": "build_list(n, f) → {list}
\n Makes a list with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nRecursive process; time: O(n)
, space: O(n)
.\n
\n
",
+ "meta": "func"
+ },
+ "display": {
+ "title": "display(v, s) \u2192 {value}",
+ "description": "display(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console. The notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "draw_data": {
+ "title": "draw_data(x) \u2192 {value}",
+ "description": "draw_data(x) → {value}
\n visualizes x
in a separate drawing\narea in the Source Academy using a box-and-pointer diagram; time, space:\nO(n), where n is the number of data structures such as\npairs in x
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_list": {
+ "title": "enum_list(start, end) \u2192 {list}",
+ "description": "enum_list(start, end) → {list}
\n Returns a list that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "equal": {
+ "title": "equal(x, y) \u2192 {boolean}",
+ "description": "equal(x, y) → {boolean}
\n Returns true
if both\nhave the same structure with respect to pair
,\nand the same numbers, boolean values, functions or empty list\nat corresponding leave positions (places that are not themselves pairs),\nand false
otherwise; time, space:\nO(n)
, where n
is the number of pairs in\nx
.\n
\n
",
+ "meta": "func"
+ },
+ "error": {
+ "title": "error(v, s) \u2192 {value}",
+ "description": "error(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console with error flag. \nThe evaluation\nof any call of
error
aborts the running program immediately.\nThe notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "filter": {
+ "title": "filter(pred, xs) \u2192 {list}",
+ "description": "filter(pred, xs) → {list}
\n Returns a list that contains\nonly those elements for which the one-argument function\npred
\nreturns true
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "for_each": {
+ "title": "for_each(f, xs) \u2192 {boolean}",
+ "description": "for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the list xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nfor_each(fun, list(1, 2))
results in the calls\nfun(1)
and fun(2)
.\n
\n
",
+ "meta": "func"
+ },
+ "head": {
+ "title": "head(p) \u2192 {value}",
+ "description": "head(p) → {value}
\n returns head (first component) of given pair p
\n
\n
",
+ "meta": "func"
+ },
+ "is_boolean": {
+ "title": "is_boolean(v) \u2192 {boolean}",
+ "description": "is_boolean(v) → {boolean}
\n checks whether a given value is a boolean\n
\n
",
+ "meta": "func"
+ },
+ "is_function": {
+ "title": "is_function(v) \u2192 {boolean}",
+ "description": "is_function(v) → {boolean}
\n checks whether a given value is a function\n
\n
",
+ "meta": "func"
+ },
+ "is_list": {
+ "title": "is_list(xs) \u2192 {xs}",
+ "description": "is_list(xs) → {xs}
\n Returns true
if\nxs
is a list as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of tail
operations that can be applied to xs
.\nrecurses down the list and checks that it ends with the empty list null\n
\n
",
+ "meta": "func"
+ },
+ "is_null": {
+ "title": "is_null(x) \u2192 {boolean}",
+ "description": "is_null(x) → {boolean}
\n returns true
if x
is the\nempty list null
, and false
otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_number": {
+ "title": "is_number(v) \u2192 {boolean}",
+ "description": "is_number(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_pair": {
+ "title": "is_pair(x) \u2192 {boolean}",
+ "description": "is_pair(x) → {boolean}
\n returns true
if x
is a\npair and false otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_string": {
+ "title": "is_string(v) \u2192 {boolean}",
+ "description": "is_string(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_undefined": {
+ "title": "is_undefined(v) \u2192 {boolean}",
+ "description": "is_undefined(v) → {boolean}
\n checks whether a given value is the special value undefined
\n
\n
",
+ "meta": "func"
+ },
+ "length": {
+ "title": "length(xs) \u2192 {number}",
+ "description": "length(xs) → {number}
\n Returns the length of the list\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list": {
+ "title": "list() \u2192 {list}",
+ "description": "list() → {list}
\n Given n
values, returns a list of length n
.\nThe elements of the list are the given values in the given order.\n
\n
",
+ "meta": "func"
+ },
+ "list_ref": {
+ "title": "list_ref(xs, n) \u2192 {value}",
+ "description": "list_ref(xs, n) → {value}
\n Returns the element\nof list xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_string": {
+ "title": "list_to_string(xs) \u2192 {string}",
+ "description": "list_to_string(xs) → {string}
\n Returns a string that represents\nlist xs
using the text-based box-and-pointer notation\n[...]
.\n
\n
",
+ "meta": "func"
+ },
+ "map": {
+ "title": "map(f, xs) \u2192 {list}",
+ "description": "map(f, xs) → {list}
\n Returns a list that results from list\nxs
by element-wise application of unary function f
. \nRecursive process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nf
is applied element-by-element:\nmap(f, list(1, 2))
results in list(f(1), f(2))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_abs": {
+ "title": "math_abs(x) \u2192 {number}",
+ "description": "math_abs(x) → {number}
\n computes the absolute value of x; the result has the same magnitude as x
but has positive sign.\n
\n
",
+ "meta": "func"
+ },
+ "math_acos": {
+ "title": "math_acos(x) \u2192 {number}",
+ "description": "math_acos(x) → {number}
\n computes the arc cosine of x
. \nThe result is expressed in radians and ranges from +0 to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_acosh": {
+ "title": "math_acosh(x) \u2192 {number}",
+ "description": "math_acosh(x) → {number}
\n computes the inverse hyperbolic cosine of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_asin": {
+ "title": "math_asin(x) \u2192 {number}",
+ "description": "math_asin(x) → {number}
\n computes the arc sine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_asinh": {
+ "title": "math_asinh(x) \u2192 {number}",
+ "description": "math_asinh(x) → {number}
\n computes the inverse hyperbolic \nsine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan": {
+ "title": "math_atan(x) \u2192 {number}",
+ "description": "math_atan(x) → {number}
\n computes the arc tangent of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan2": {
+ "title": "math_atan2(y, x) \u2192 {number}",
+ "description": "math_atan2(y, x) → {number}
\n computes the arc tangent of the quotient y
/ x
of the arguments y
and x
, where the signs of y
and x
are used to determine the quadrant of the result. Note that it is intentional and traditional for the two-argument arc tangent function that the argument named y
be first and the argument named x
be second. The result is expressed in radians and ranges from -π to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_atanh": {
+ "title": "math_atanh(x) \u2192 {number}",
+ "description": "math_atanh(x) → {number}
\n computes the inverse hyperbolic tangent of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_cbrt": {
+ "title": "math_cbrt(x) \u2192 {number}",
+ "description": "math_cbrt(x) → {number}
\n computes the cube root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_ceil": {
+ "title": "math_ceil(x) \u2192 {number}",
+ "description": "math_ceil(x) → {number}
\n computes the smallest (closest to -∞) Number value that is not less than x
and is an integer. If x
is already an integer, the result is x
.\nThe value of math_ceil(x) is the same as the value of -math_floor(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_clz32": {
+ "title": "math_clz32(n) \u2192 {number}",
+ "description": "math_clz32(n) → {number}
\n When math_clz32 is called with one argument
x
, the following steps are taken:\nLet n be ToUint32(x).\nLet p be the number of leading zero bits in the 32-bit binary representation of n.\nReturn p.\n
NOTE:\n
If n is 0, p will be 32. If the most significant bit of the 32-bit binary encoding of n is 1, \np will be 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_cos": {
+ "title": "math_cos(x) \u2192 {number}",
+ "description": "math_cos(x) → {number}
\n Computes the cosine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_cosh": {
+ "title": "math_cosh(x) \u2192 {number}",
+ "description": "math_cosh(x) → {number}
\n computes the hyperbolic cosine of
x
.\n
NOTE:\nThe value of cosh(x) is the same as (exp(x) + exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_exp": {
+ "title": "math_exp(x) \u2192 {number}",
+ "description": "math_exp(x) → {number}
\n computes the exponential function of x
\n(e raised to the power of x
, where e is the base of the natural logarithms).\n
\n
",
+ "meta": "func"
+ },
+ "math_expm1": {
+ "title": "math_expm1(x) \u2192 {number}",
+ "description": "math_expm1(x) → {number}
\n computes subtracting 1 from the \nexponential function of x
(e raised to the power of x
, where e is the base of \nthe natural logarithms). The result is computed in a way that is accurate even \nwhen the value of x
is close 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_floor": {
+ "title": "math_floor(x) \u2192 {number}",
+ "description": "math_floor(x) → {number}
\n computes the greatest (closest to +∞) Number value that is not greater than
x
\nand is an integer. \n
If
x
is already an integer, the result is
x
.\n
NOTE:\nThe value of math_floor(x) is the same as the value of -math_ceil(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_fround": {
+ "title": "math_fround(x) \u2192 {number}",
+ "description": "math_fround(x) → {number}
\n When math_fround is called with argument
x
, the following steps are taken:\n
- If
x
is NaN, return NaN. \n- If
x
is one of +0, -0, +∞, -∞, return x
. \n- Let x32 be the result of converting
x
to a value in IEEE 754-2008 binary32 format using roundTiesToEven mode. \n- Let x64 be the result of converting x32 to a value in IEEE 754-2008 binary64 format.
\n- Return the ECMAScript Number value corresponding to x64.
\n
\n
",
+ "meta": "func"
+ },
+ "math_hypot": {
+ "title": "math_hypot() \u2192 {number}",
+ "description": "math_hypot() → {number}
\n computes the square root\nof the sum of squares of its arguments.\n
If no arguments are passed, the result is +0.\n
\n
",
+ "meta": "func"
+ },
+ "math_imul": {
+ "title": "math_imul(x, x) \u2192 {number}",
+ "description": "math_imul(x, x) → {number}
\n When math_imul is called with arguments
x
and
y
,\nthe following steps are taken:\n
\n- Let a be ToUint32(x).
\n- Let b be ToUint32(y).
\n- Let product be (a × b) modulo 232.
\n- If product ≥ 231, return product - 232; otherwise return product.
\n
\n
",
+ "meta": "func"
+ },
+ "math_log": {
+ "title": "math_log(x) \u2192 {number}",
+ "description": "math_log(x) → {number}
\n Computes the natural logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log1p": {
+ "title": "math_log1p(x) \u2192 {number}",
+ "description": "math_log1p(x) → {number}
\n computes the natural logarithm of 1 + x
. The result is computed in a way that is accurate even when the value of x
is close to zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_log2": {
+ "title": "math_log2(x) \u2192 {number}",
+ "description": "math_log2(x) → {number}
\n computes the base 2 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log10": {
+ "title": "math_log10(x) \u2192 {number}",
+ "description": "math_log10(x) → {number}
\n computes the base 10 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_max": {
+ "title": "math_max() \u2192 {number}",
+ "description": "math_max() → {number}
\n Given zero or more numbers, returns the largest of them.\n
If no arguments are given, the result is -∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the largest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_min": {
+ "title": "math_min() \u2192 {number}",
+ "description": "math_min() → {number}
\n Given zero or more arguments, returns the smallest of them.\n
If no arguments are given, the result is +∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the smallest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_pow": {
+ "title": "math_pow(base, exponent) \u2192 {number}",
+ "description": "math_pow(base, exponent) → {number}
\n Computes the result of raising base to \nthe power of exponent.\n
\n
",
+ "meta": "func"
+ },
+ "math_random": {
+ "title": "math_random() \u2192 {number}",
+ "description": "math_random() → {number}
\n Returns a number value with positive sign, greater than or equal to 0 but less than 1, \nchosen randomly or pseudo randomly with approximately uniform distribution over that \nrange, using an implementation-dependent algorithm or strategy. This function takes no arguments.\nEach math_random function created for distinct realms must produce a distinct sequence \nof values from successive calls.\n
\n
",
+ "meta": "func"
+ },
+ "math_round": {
+ "title": "math_round(x) \u2192 {number}",
+ "description": "math_round(x) → {number}
\n Returns the number value that is closest to x
and is an integer. \n
If two integers are equally close to x
, then the result is the Number value \nthat is closer to +∞. If x
is already an integer, the result is x
.\nNOTE 1:\nmath_round(3.5) returns 4, but math_round(-3.5) returns -3.\n
\n
",
+ "meta": "func"
+ },
+ "math_sign": {
+ "title": "math_sign(x) \u2192 {number}",
+ "description": "math_sign(x) → {number}
\n Computes the sign of x
, indicating whether x
is positive, negative, or zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_sin": {
+ "title": "math_sin(x) \u2192 {number}",
+ "description": "math_sin(x) → {number}
\n Computes the sine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_sinh": {
+ "title": "math_sinh(x) \u2192 {number}",
+ "description": "math_sinh(x) → {number}
\n Computes the hyperbolic sine of
x
.\n
NOTE:\nThe value of sinh(x) is the same as (exp(x) - exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_sqrt": {
+ "title": "math_sqrt(x) \u2192 {number}",
+ "description": "math_sqrt(x) → {number}
\n Computes the square root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_tan": {
+ "title": "math_tan(x) \u2192 {number}",
+ "description": "math_tan(x) → {number}
\n Computes the tangent of x
. The argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_tanh": {
+ "title": "math_tanh(x) \u2192 {number}",
+ "description": "math_tanh(x) → {number}
\n Computes the hyperbolic tangent of
x
.\n
NOTE:\nThe value of
math_tanh(x)
is the same as\n
(exp(x) - exp(-x))/(exp(x) + exp(-x))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_trunc": {
+ "title": "math_trunc(x) \u2192 {number}",
+ "description": "math_trunc(x) → {number}
\n Computes the integral part of the number x
,\nremoving any fractional digits.\n
\n
",
+ "meta": "func"
+ },
+ "member": {
+ "title": "member(v, xs) \u2192 {list}",
+ "description": "member(v, xs) → {list}
\n Returns first postfix sublist\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the list.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "pair": {
+ "title": "pair(x, y) \u2192 {pair}",
+ "description": "pair(x, y) → {pair}
\n makes a pair whose head (first component) is x
\nand whose tail (second component) is y
.\n
\n
",
+ "meta": "func"
+ },
+ "parse_int": {
+ "title": "parse_int(s, i) \u2192 {number}",
+ "description": "parse_int(s, i) → {number}
\n Interprets a given string
s
as an integer, \nusing the positive integer
i
as radix, \nand returns the respective value.\n
Examples:
parse_int(\"909\", 10)
returns the number \n
909
, and
parse_int(\"-1111\", 2)
returns the number \n
-15
.
\nSee
ECMAScript Specification, Section 18.2.5 for details.\n
\n
",
+ "meta": "func"
+ },
+ "prompt": {
+ "title": "prompt(s) \u2192 {string}",
+ "description": "prompt(s) → {string}
\n Pops up a window that displays the string s
, provides\nan input line for the user to enter a text, a Cancel
button and an OK
button. \nThe call of prompt
\nsuspends execution of the program until one of the two buttons is pressed. If \nthe OK
button is pressed, prompt
returns the entered text as a string.\nIf the Cancel
button is pressed, prompt
returns a non-string value.\n
\n
",
+ "meta": "func"
+ },
+ "remove": {
+ "title": "remove(v, xs) \u2192 {list}",
+ "description": "remove(v, xs) → {list}
\n Returns a list that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. Recursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "remove_all": {
+ "title": "remove_all(v, xs) \u2192 {list}",
+ "description": "remove_all(v, xs) → {list}
\n Returns a list that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. \nRecursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "reverse": {
+ "title": "reverse(xs) \u2192 {list}",
+ "description": "reverse(xs) → {list}
\n Returns list xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result list.\n
\n
",
+ "meta": "func"
+ },
+ "runtime": {
+ "title": "runtime() \u2192 {number}",
+ "description": "runtime() → {number}
\n Returns number of milliseconds elapsed since January 1, 1970 00:00:00 UTC.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "stringify": {
+ "title": "stringify(v) \u2192 {string}",
+ "description": "stringify(v) → {string}
\n returns a string that represents the value
v
, using a\nnotation that is is consistent with \n
JSON, \nbut also displays
undefined
and function objects.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "tail": {
+ "title": "tail(p) \u2192 {value}",
+ "description": "tail(p) → {value}
\n returns tail (second component of given pair p
\n
\n
",
+ "meta": "func"
+ }
+}
\ No newline at end of file
diff --git a/src/editors/ace/docTooltip/source_3.json b/src/editors/ace/docTooltip/source_3.json
new file mode 100644
index 000000000..6cb03faad
--- /dev/null
+++ b/src/editors/ace/docTooltip/source_3.json
@@ -0,0 +1,512 @@
+{
+ "Infinity": {
+ "title": "Infinity:number",
+ "description": "",
+ "meta": "const"
+ },
+ "math_LN2": {
+ "title": "math_LN2:number",
+ "description": "math_LN2:number
\n The Number value for the natural logarithm of 2, \nwhich is approximately 0.6931471805599453.\n
\n
",
+ "meta": "const"
+ },
+ "math_LN10": {
+ "title": "math_LN10:number",
+ "description": "math_LN10:number
\n The Number value for the natural logarithm of 10, \nwhich is approximately 2.302585092994046.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG2E": {
+ "title": "math_LOG2E:number",
+ "description": "math_LOG2E:number
\n The Number value for the base-2 logarithm of eℝ, the base of the natural logarithms; \nthis value is approximately 1.4426950408889634.\n
NOTE:\nThe value of math_LOG2E is approximately the reciprocal of the value of math_LN2.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG10E": {
+ "title": "math_LOG10E:number",
+ "description": "math_LOG10E:number
\n The Number value for the base-10 logarithm of e, \nthe base of the natural logarithms; this value is approximately 0.4342944819032518.\n
NOTE:\nThe value of math_LOG10E is approximately the reciprocal of the value of math_LN10.\n
\n
",
+ "meta": "const"
+ },
+ "math_PI": {
+ "title": "math_PI:number",
+ "description": "math_PI:number
\n The Number value for π, the ratio of the circumference of a circle to its diameter, \nwhich is approximately 3.1415926535897932.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT1_2": {
+ "title": "math_SQRT1_2:number",
+ "description": "math_SQRT1_2:number
\n The Number value for the square root of 0.5, which is approximately 0.7071067811865476.\n
NOTE:\nThe value of math_SQRT1_2 is approximately the reciprocal of the value of math_SQRT2.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT2": {
+ "title": "math_SQRT2:number",
+ "description": "math_SQRT2:number
\n The Number value for the square root of 2, which is approximately 1.4142135623730951.\n
\n
",
+ "meta": "const"
+ },
+ "NaN": {
+ "title": "NaN:number",
+ "description": "",
+ "meta": "const"
+ },
+ "undefined": {
+ "title": "undefined:undefined",
+ "description": "",
+ "meta": "const"
+ },
+ "accumulate": {
+ "title": "accumulate(f, initial, xs) \u2192 {value}",
+ "description": "accumulate(f, initial, xs) → {value}
\n Applies binary\nfunction f
to the elements of xs
from\nright-to-left order, first applying f
to the last element\nand the value initial
, resulting in r
1,\nthen to the \nsecond-last element and r
1, resulting in\nr
2,\netc, and finally\nto the first element and r
n-1, where\nn
is the length of the\nlist. Thus, accumulate(f,zero,list(1,2,3))
results in\nf(1, f(2, f(3, zero)))
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
\nassuming f
takes constant time.\n
\n
",
+ "meta": "func"
+ },
+ "append": {
+ "title": "append(xs, ys) \u2192 {list}",
+ "description": "append(xs, ys) → {list}
\n Returns a list that results from \nappending the list ys
to the list xs
.\nRecursive process; time: O(n)
, space:\nO(n)
, where n
is the length of xs
.\nIn the result, null at the end of the first argument list\nis replaced by the second argument, regardless what the second\nargument consists of.\n
\n
",
+ "meta": "func"
+ },
+ "array_length": {
+ "title": "array_length(x) \u2192 {number}",
+ "description": "array_length(x) → {number}
\n returns\nthe current length of array x
, which is 1 plus the\nhighest index that has been used so far in an array assignment on \nx
. Here literal array expressions are counted too: The\narray [10, 20, 30]
has a length of 3.\n
\n
",
+ "meta": "func"
+ },
+ "build_list": {
+ "title": "build_list(n, f) \u2192 {list}",
+ "description": "build_list(n, f) → {list}
\n Makes a list with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nRecursive process; time: O(n)
, space: O(n)
.\n
\n
",
+ "meta": "func"
+ },
+ "build_stream": {
+ "title": "build_stream(n, f) \u2192 {stream}",
+ "description": "build_stream(n, f) → {stream}
\n Makes a stream with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nLazy? Yes: The result stream forces the application of f
\n for the next element\n
\n
",
+ "meta": "func"
+ },
+ "display": {
+ "title": "display(v, s) \u2192 {value}",
+ "description": "display(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console. The notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "draw_data": {
+ "title": "draw_data(x) \u2192 {value}",
+ "description": "draw_data(x) → {value}
\n visualizes x
in a separate drawing\narea in the Source Academy using a box-and-pointer diagram; time, space:\nO(n), where n is the number of data structures such as\npairs in x
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_list": {
+ "title": "enum_list(start, end) \u2192 {list}",
+ "description": "enum_list(start, end) → {list}
\n Returns a list that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_stream": {
+ "title": "enum_stream(start, end) \u2192 {stream}",
+ "description": "enum_stream(start, end) → {stream}
\n Returns a stream that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nLazy? Yes: The result stream forces the construction of\n each next element\n
\n
",
+ "meta": "func"
+ },
+ "equal": {
+ "title": "equal(x, y) \u2192 {boolean}",
+ "description": "equal(x, y) → {boolean}
\n Returns true
if both\nhave the same structure with respect to pair
,\nand the same numbers, boolean values, functions or empty list\nat corresponding leave positions (places that are not themselves pairs),\nand false
otherwise; time, space:\nO(n)
, where n
is the number of pairs in\nx
.\n
\n
",
+ "meta": "func"
+ },
+ "error": {
+ "title": "error(v, s) \u2192 {value}",
+ "description": "error(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console with error flag. \nThe evaluation\nof any call of
error
aborts the running program immediately.\nThe notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "eval_stream": {
+ "title": "eval_stream(s, n) \u2192 {list}",
+ "description": "eval_stream(s, n) → {list}
\n Constructs the list of the first n
elements\nof a given stream s
\nLazy? Sort-of: eval_stream
only forces the computation of\nthe first n
elements, and leaves the rest of\nthe stream untouched.\n
\n
",
+ "meta": "func"
+ },
+ "filter": {
+ "title": "filter(pred, xs) \u2192 {list}",
+ "description": "filter(pred, xs) → {list}
\n Returns a list that contains\nonly those elements for which the one-argument function\npred
\nreturns true
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "for_each": {
+ "title": "for_each(f, xs) \u2192 {boolean}",
+ "description": "for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the list xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nfor_each(fun, list(1, 2))
results in the calls\nfun(1)
and fun(2)
.\n
\n
",
+ "meta": "func"
+ },
+ "head": {
+ "title": "head(p) \u2192 {value}",
+ "description": "head(p) → {value}
\n returns head (first component) of given pair p
\n
\n
",
+ "meta": "func"
+ },
+ "integers_from": {
+ "title": "integers_from(start) \u2192 {stream}",
+ "description": "integers_from(start) → {stream}
\n Returns infinite stream if integers starting \nat given number n
using a step size of 1.\nLazy? Yes: The result stream forces the construction of\n each next element\n
\n
",
+ "meta": "func"
+ },
+ "is_array": {
+ "title": "is_array(x) \u2192 {boolean}",
+ "description": "is_array(x) → {boolean}
\n returns true
if x
\nis an array, and false
if it is not.\n
\n
",
+ "meta": "func"
+ },
+ "is_boolean": {
+ "title": "is_boolean(v) \u2192 {boolean}",
+ "description": "is_boolean(v) → {boolean}
\n checks whether a given value is a boolean\n
\n
",
+ "meta": "func"
+ },
+ "is_function": {
+ "title": "is_function(v) \u2192 {boolean}",
+ "description": "is_function(v) → {boolean}
\n checks whether a given value is a function\n
\n
",
+ "meta": "func"
+ },
+ "is_list": {
+ "title": "is_list(xs) \u2192 {xs}",
+ "description": "is_list(xs) → {xs}
\n Returns true
if\nxs
is a list as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of tail
operations that can be applied to xs
.\nrecurses down the list and checks that it ends with the empty list null\n
\n
",
+ "meta": "func"
+ },
+ "is_null": {
+ "title": "is_null(x) \u2192 {boolean}",
+ "description": "is_null(x) → {boolean}
\n returns true
if x
is the\nempty list null
, and false
otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_number": {
+ "title": "is_number(v) \u2192 {boolean}",
+ "description": "is_number(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_pair": {
+ "title": "is_pair(x) \u2192 {boolean}",
+ "description": "is_pair(x) → {boolean}
\n returns true
if x
is a\npair and false otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_stream": {
+ "title": "is_stream(xs) \u2192 {boolean}",
+ "description": "is_stream(xs) → {boolean}
\n Returns true
if\nxs
is a stream as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of stream_tail
operations that can be applied to xs
.\nrecurses down the stream and checks that it ends with the empty stream null.\nLaziness: No: is_stream
needs to force the given stream.\n
\n
",
+ "meta": "func"
+ },
+ "is_string": {
+ "title": "is_string(v) \u2192 {boolean}",
+ "description": "is_string(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_undefined": {
+ "title": "is_undefined(v) \u2192 {boolean}",
+ "description": "is_undefined(v) → {boolean}
\n checks whether a given value is the special value undefined
\n
\n
",
+ "meta": "func"
+ },
+ "length": {
+ "title": "length(xs) \u2192 {number}",
+ "description": "length(xs) → {number}
\n Returns the length of the list\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list": {
+ "title": "list() \u2192 {list}",
+ "description": "list() → {list}
\n Given n
values, returns a list of length n
.\nThe elements of the list are the given values in the given order.\n
\n
",
+ "meta": "func"
+ },
+ "list_ref": {
+ "title": "list_ref(xs, n) \u2192 {value}",
+ "description": "list_ref(xs, n) → {value}
\n Returns the element\nof list xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_stream": {
+ "title": "list_to_stream(xs) \u2192 {stream}",
+ "description": "list_to_stream(xs) → {stream}
\n Given list xs
, returns a stream of same length with\nthe same elements as xs
in the same order.\nLaziness: Yes: list_to_stream
\ngoes down the list only when forced.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_string": {
+ "title": "list_to_string(xs) \u2192 {string}",
+ "description": "list_to_string(xs) → {string}
\n Returns a string that represents\nlist xs
using the text-based box-and-pointer notation\n[...]
.\n
\n
",
+ "meta": "func"
+ },
+ "map": {
+ "title": "map(f, xs) \u2192 {list}",
+ "description": "map(f, xs) → {list}
\n Returns a list that results from list\nxs
by element-wise application of unary function f
. \nRecursive process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nf
is applied element-by-element:\nmap(f, list(1, 2))
results in list(f(1), f(2))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_abs": {
+ "title": "math_abs(x) \u2192 {number}",
+ "description": "math_abs(x) → {number}
\n computes the absolute value of x; the result has the same magnitude as x
but has positive sign.\n
\n
",
+ "meta": "func"
+ },
+ "math_acos": {
+ "title": "math_acos(x) \u2192 {number}",
+ "description": "math_acos(x) → {number}
\n computes the arc cosine of x
. \nThe result is expressed in radians and ranges from +0 to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_acosh": {
+ "title": "math_acosh(x) \u2192 {number}",
+ "description": "math_acosh(x) → {number}
\n computes the inverse hyperbolic cosine of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_asin": {
+ "title": "math_asin(x) \u2192 {number}",
+ "description": "math_asin(x) → {number}
\n computes the arc sine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_asinh": {
+ "title": "math_asinh(x) \u2192 {number}",
+ "description": "math_asinh(x) → {number}
\n computes the inverse hyperbolic \nsine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan": {
+ "title": "math_atan(x) \u2192 {number}",
+ "description": "math_atan(x) → {number}
\n computes the arc tangent of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan2": {
+ "title": "math_atan2(y, x) \u2192 {number}",
+ "description": "math_atan2(y, x) → {number}
\n computes the arc tangent of the quotient y
/ x
of the arguments y
and x
, where the signs of y
and x
are used to determine the quadrant of the result. Note that it is intentional and traditional for the two-argument arc tangent function that the argument named y
be first and the argument named x
be second. The result is expressed in radians and ranges from -π to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_atanh": {
+ "title": "math_atanh(x) \u2192 {number}",
+ "description": "math_atanh(x) → {number}
\n computes the inverse hyperbolic tangent of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_cbrt": {
+ "title": "math_cbrt(x) \u2192 {number}",
+ "description": "math_cbrt(x) → {number}
\n computes the cube root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_ceil": {
+ "title": "math_ceil(x) \u2192 {number}",
+ "description": "math_ceil(x) → {number}
\n computes the smallest (closest to -∞) Number value that is not less than x
and is an integer. If x
is already an integer, the result is x
.\nThe value of math_ceil(x) is the same as the value of -math_floor(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_clz32": {
+ "title": "math_clz32(n) \u2192 {number}",
+ "description": "math_clz32(n) → {number}
\n When math_clz32 is called with one argument
x
, the following steps are taken:\nLet n be ToUint32(x).\nLet p be the number of leading zero bits in the 32-bit binary representation of n.\nReturn p.\n
NOTE:\n
If n is 0, p will be 32. If the most significant bit of the 32-bit binary encoding of n is 1, \np will be 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_cos": {
+ "title": "math_cos(x) \u2192 {number}",
+ "description": "math_cos(x) → {number}
\n Computes the cosine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_cosh": {
+ "title": "math_cosh(x) \u2192 {number}",
+ "description": "math_cosh(x) → {number}
\n computes the hyperbolic cosine of
x
.\n
NOTE:\nThe value of cosh(x) is the same as (exp(x) + exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_exp": {
+ "title": "math_exp(x) \u2192 {number}",
+ "description": "math_exp(x) → {number}
\n computes the exponential function of x
\n(e raised to the power of x
, where e is the base of the natural logarithms).\n
\n
",
+ "meta": "func"
+ },
+ "math_expm1": {
+ "title": "math_expm1(x) \u2192 {number}",
+ "description": "math_expm1(x) → {number}
\n computes subtracting 1 from the \nexponential function of x
(e raised to the power of x
, where e is the base of \nthe natural logarithms). The result is computed in a way that is accurate even \nwhen the value of x
is close 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_floor": {
+ "title": "math_floor(x) \u2192 {number}",
+ "description": "math_floor(x) → {number}
\n computes the greatest (closest to +∞) Number value that is not greater than
x
\nand is an integer. \n
If
x
is already an integer, the result is
x
.\n
NOTE:\nThe value of math_floor(x) is the same as the value of -math_ceil(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_fround": {
+ "title": "math_fround(x) \u2192 {number}",
+ "description": "math_fround(x) → {number}
\n When math_fround is called with argument
x
, the following steps are taken:\n
- If
x
is NaN, return NaN. \n- If
x
is one of +0, -0, +∞, -∞, return x
. \n- Let x32 be the result of converting
x
to a value in IEEE 754-2008 binary32 format using roundTiesToEven mode. \n- Let x64 be the result of converting x32 to a value in IEEE 754-2008 binary64 format.
\n- Return the ECMAScript Number value corresponding to x64.
\n
\n
",
+ "meta": "func"
+ },
+ "math_hypot": {
+ "title": "math_hypot() \u2192 {number}",
+ "description": "math_hypot() → {number}
\n computes the square root\nof the sum of squares of its arguments.\n
If no arguments are passed, the result is +0.\n
\n
",
+ "meta": "func"
+ },
+ "math_imul": {
+ "title": "math_imul(x, x) \u2192 {number}",
+ "description": "math_imul(x, x) → {number}
\n When math_imul is called with arguments
x
and
y
,\nthe following steps are taken:\n
\n- Let a be ToUint32(x).
\n- Let b be ToUint32(y).
\n- Let product be (a × b) modulo 232.
\n- If product ≥ 231, return product - 232; otherwise return product.
\n
\n
",
+ "meta": "func"
+ },
+ "math_log": {
+ "title": "math_log(x) \u2192 {number}",
+ "description": "math_log(x) → {number}
\n Computes the natural logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log1p": {
+ "title": "math_log1p(x) \u2192 {number}",
+ "description": "math_log1p(x) → {number}
\n computes the natural logarithm of 1 + x
. The result is computed in a way that is accurate even when the value of x
is close to zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_log2": {
+ "title": "math_log2(x) \u2192 {number}",
+ "description": "math_log2(x) → {number}
\n computes the base 2 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log10": {
+ "title": "math_log10(x) \u2192 {number}",
+ "description": "math_log10(x) → {number}
\n computes the base 10 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_max": {
+ "title": "math_max() \u2192 {number}",
+ "description": "math_max() → {number}
\n Given zero or more numbers, returns the largest of them.\n
If no arguments are given, the result is -∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the largest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_min": {
+ "title": "math_min() \u2192 {number}",
+ "description": "math_min() → {number}
\n Given zero or more arguments, returns the smallest of them.\n
If no arguments are given, the result is +∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the smallest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_pow": {
+ "title": "math_pow(base, exponent) \u2192 {number}",
+ "description": "math_pow(base, exponent) → {number}
\n Computes the result of raising base to \nthe power of exponent.\n
\n
",
+ "meta": "func"
+ },
+ "math_random": {
+ "title": "math_random() \u2192 {number}",
+ "description": "math_random() → {number}
\n Returns a number value with positive sign, greater than or equal to 0 but less than 1, \nchosen randomly or pseudo randomly with approximately uniform distribution over that \nrange, using an implementation-dependent algorithm or strategy. This function takes no arguments.\nEach math_random function created for distinct realms must produce a distinct sequence \nof values from successive calls.\n
\n
",
+ "meta": "func"
+ },
+ "math_round": {
+ "title": "math_round(x) \u2192 {number}",
+ "description": "math_round(x) → {number}
\n Returns the number value that is closest to x
and is an integer. \n
If two integers are equally close to x
, then the result is the Number value \nthat is closer to +∞. If x
is already an integer, the result is x
.\nNOTE 1:\nmath_round(3.5) returns 4, but math_round(-3.5) returns -3.\n
\n
",
+ "meta": "func"
+ },
+ "math_sign": {
+ "title": "math_sign(x) \u2192 {number}",
+ "description": "math_sign(x) → {number}
\n Computes the sign of x
, indicating whether x
is positive, negative, or zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_sin": {
+ "title": "math_sin(x) \u2192 {number}",
+ "description": "math_sin(x) → {number}
\n Computes the sine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_sinh": {
+ "title": "math_sinh(x) \u2192 {number}",
+ "description": "math_sinh(x) → {number}
\n Computes the hyperbolic sine of
x
.\n
NOTE:\nThe value of sinh(x) is the same as (exp(x) - exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_sqrt": {
+ "title": "math_sqrt(x) \u2192 {number}",
+ "description": "math_sqrt(x) → {number}
\n Computes the square root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_tan": {
+ "title": "math_tan(x) \u2192 {number}",
+ "description": "math_tan(x) → {number}
\n Computes the tangent of x
. The argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_tanh": {
+ "title": "math_tanh(x) \u2192 {number}",
+ "description": "math_tanh(x) → {number}
\n Computes the hyperbolic tangent of
x
.\n
NOTE:\nThe value of
math_tanh(x)
is the same as\n
(exp(x) - exp(-x))/(exp(x) + exp(-x))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_trunc": {
+ "title": "math_trunc(x) \u2192 {number}",
+ "description": "math_trunc(x) → {number}
\n Computes the integral part of the number x
,\nremoving any fractional digits.\n
\n
",
+ "meta": "func"
+ },
+ "member": {
+ "title": "member(v, xs) \u2192 {list}",
+ "description": "member(v, xs) → {list}
\n Returns first postfix sublist\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the list.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "pair": {
+ "title": "pair(x, y) \u2192 {pair}",
+ "description": "pair(x, y) → {pair}
\n makes a pair whose head (first component) is x
\nand whose tail (second component) is y
.\n
\n
",
+ "meta": "func"
+ },
+ "parse_int": {
+ "title": "parse_int(s, i) \u2192 {number}",
+ "description": "parse_int(s, i) → {number}
\n Interprets a given string
s
as an integer, \nusing the positive integer
i
as radix, \nand returns the respective value.\n
Examples:
parse_int(\"909\", 10)
returns the number \n
909
, and
parse_int(\"-1111\", 2)
returns the number \n
-15
.
\nSee
ECMAScript Specification, Section 18.2.5 for details.\n
\n
",
+ "meta": "func"
+ },
+ "prompt": {
+ "title": "prompt(s) \u2192 {string}",
+ "description": "prompt(s) → {string}
\n Pops up a window that displays the string s
, provides\nan input line for the user to enter a text, a Cancel
button and an OK
button. \nThe call of prompt
\nsuspends execution of the program until one of the two buttons is pressed. If \nthe OK
button is pressed, prompt
returns the entered text as a string.\nIf the Cancel
button is pressed, prompt
returns a non-string value.\n
\n
",
+ "meta": "func"
+ },
+ "remove": {
+ "title": "remove(v, xs) \u2192 {list}",
+ "description": "remove(v, xs) → {list}
\n Returns a list that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. Recursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "remove_all": {
+ "title": "remove_all(v, xs) \u2192 {list}",
+ "description": "remove_all(v, xs) → {list}
\n Returns a list that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. \nRecursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "reverse": {
+ "title": "reverse(xs) \u2192 {list}",
+ "description": "reverse(xs) → {list}
\n Returns list xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result list.\n
\n
",
+ "meta": "func"
+ },
+ "runtime": {
+ "title": "runtime() \u2192 {number}",
+ "description": "runtime() → {number}
\n Returns number of milliseconds elapsed since January 1, 1970 00:00:00 UTC.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "set_head": {
+ "title": "set_head(p, x) \u2192 {undefined}",
+ "description": "set_head(p, x) → {undefined}
\n changes the pair p
such that its head is x
.\n
\n
",
+ "meta": "func"
+ },
+ "set_tail": {
+ "title": "set_tail(p, x) \u2192 {undefined}",
+ "description": "set_tail(p, x) → {undefined}
\n changes the pair p
such that its tail is x
.\n
\n
",
+ "meta": "func"
+ },
+ "stream": {
+ "title": "stream() \u2192 {stream}",
+ "description": "stream() → {stream}
\n Given n
values, returns a stream of length n
.\nThe elements of the stream are the given values in the given order.\nLazy? No: A\ncomplete list is generated, \nand then a stream using list_to_stream
is generated from it.\n
\n
",
+ "meta": "func"
+ },
+ "stream_append": {
+ "title": "stream_append(xs, ys) \u2192 {stream}",
+ "description": "stream_append(xs, ys) → {stream}
\n Returns a stream that results from \nappending the stream ys
to the stream xs
.\nIn the result, null at the end of the first argument stream\nis replaced by the second argument, regardless what the second\nargument consists of.\nLazy? Yes: the result stream forces the actual append operation\n
\n
",
+ "meta": "func"
+ },
+ "stream_filter": {
+ "title": "stream_filter(pred, xs) \u2192 {stream}",
+ "description": "stream_filter(pred, xs) → {stream}
\n Returns a stream that contains\nonly those elements of given stream xs
\nfor which the one-argument function\npred
\nreturns true
.\nLazy? Yes: The result stream forces the construction of\n each next element. Of course, the construction\n of the next element needs to go down the stream\n until an element is found for which pred
holds.\n
\n
",
+ "meta": "func"
+ },
+ "stream_for_each": {
+ "title": "stream_for_each(f, xs) \u2192 {boolean}",
+ "description": "stream_for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the stream xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nstream_for_each(f, stream(1, 2))
results in the calls\nf(1)
and f(2)
.\nLazy? No: stream_for_each
\nforces the exploration of the entire stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_length": {
+ "title": "stream_length(xs) \u2192 {number}",
+ "description": "stream_length(xs) → {number}
\n Returns the length of the stream\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\nLazy? No: The function needs to explore the whole stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_map": {
+ "title": "stream_map(f, xs) \u2192 {stream}",
+ "description": "stream_map(f, xs) → {stream}
\n Returns a stream that results from stream\nxs
by element-wise application \nof unary function f
. \nf
is applied element-by-element:\nstream_map(f, stream(1,2))
results in\nthe same as stream(f(1),f(2))
.\nLazy? Yes: The argument stream is only explored as forced by\n the result stream.\n
\n
",
+ "meta": "func"
+ },
+ "stream_member": {
+ "title": "stream_member(v, xs) \u2192 {stream}",
+ "description": "stream_member(v, xs) → {stream}
\n Returns first postfix substream\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the stream.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\nLazy? Sort-of: stream_member
\nforces the stream only until the element \nis found.\n
\n
",
+ "meta": "func"
+ },
+ "stream_ref": {
+ "title": "stream_ref(xs, n) \u2192 {value}",
+ "description": "stream_ref(xs, n) → {value}
\n Returns the element\nof stream xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\nLazy? Sort-of: stream_ref
only forces the computation of\n the first n
elements, and leaves the rest of\n the stream untouched.\n
\n
",
+ "meta": "func"
+ },
+ "stream_remove": {
+ "title": "stream_remove(v, xs) \u2192 {stream}",
+ "description": "stream_remove(v, xs) → {stream}
\n Returns a stream that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nstream if there is no occurrence. \nLazy? Yes: the result stream forces the construction of each next element\n
\n
",
+ "meta": "func"
+ },
+ "stream_remove_all": {
+ "title": "stream_remove_all(v, xs) \u2192 {stream}",
+ "description": "stream_remove_all(v, xs) → {stream}
\n Returns a stream that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nstream if there is no occurrence. \nRecursive process.\nLazy? Yes: the result stream forces the construction of each next \nelement\n
\n
",
+ "meta": "func"
+ },
+ "stream_reverse": {
+ "title": "stream_reverse(xs) \u2192 {stream}",
+ "description": "stream_reverse(xs) → {stream}
\n Returns stream xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result stream.\nLazy? No: stream_reverse
\nforces the exploration of the entire stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_tail": {
+ "title": "stream_tail(xs) \u2192 {Stream}",
+ "description": "stream_tail(xs) → {Stream}
\n assumes that the tail (second component) of the\npair {x} is a nullary function, and returns the result of\napplying that function. Throws an exception if the argument \nis not a pair, or if the tail is not a function.\nLaziness: Yes: {stream_tail} only forces the direct tail \nstream, but not the rest of the stream, i.e. not the tail \nof the tail, etc.\n
\n
",
+ "meta": "func"
+ },
+ "stream_to_list": {
+ "title": "stream_to_list(xs) \u2192 {list}",
+ "description": "stream_to_list(xs) → {list}
\n Given stream xs
, returns a list of same length with\nthe same elements as xs
in the same order.\nLaziness: No: stream_to_list
needs to force the whole \nstream.\n
\n
",
+ "meta": "func"
+ },
+ "stringify": {
+ "title": "stringify(v) \u2192 {string}",
+ "description": "stringify(v) → {string}
\n returns a string that represents the value
v
, using a\nnotation that is is consistent with \n
JSON, \nbut also displays
undefined
and function objects.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "tail": {
+ "title": "tail(p) \u2192 {value}",
+ "description": "tail(p) → {value}
\n returns tail (second component of given pair p
\n
\n
",
+ "meta": "func"
+ }
+}
\ No newline at end of file
diff --git a/src/editors/ace/docTooltip/source_3_concurrent.json b/src/editors/ace/docTooltip/source_3_concurrent.json
new file mode 100644
index 000000000..68ac71e4e
--- /dev/null
+++ b/src/editors/ace/docTooltip/source_3_concurrent.json
@@ -0,0 +1,527 @@
+{
+ "Infinity": {
+ "title": "Infinity:number",
+ "description": "",
+ "meta": "const"
+ },
+ "math_LN2": {
+ "title": "math_LN2:number",
+ "description": "math_LN2:number
\n The Number value for the natural logarithm of 2, \nwhich is approximately 0.6931471805599453.\n
\n
",
+ "meta": "const"
+ },
+ "math_LN10": {
+ "title": "math_LN10:number",
+ "description": "math_LN10:number
\n The Number value for the natural logarithm of 10, \nwhich is approximately 2.302585092994046.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG2E": {
+ "title": "math_LOG2E:number",
+ "description": "math_LOG2E:number
\n The Number value for the base-2 logarithm of eℝ, the base of the natural logarithms; \nthis value is approximately 1.4426950408889634.\n
NOTE:\nThe value of math_LOG2E is approximately the reciprocal of the value of math_LN2.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG10E": {
+ "title": "math_LOG10E:number",
+ "description": "math_LOG10E:number
\n The Number value for the base-10 logarithm of e, \nthe base of the natural logarithms; this value is approximately 0.4342944819032518.\n
NOTE:\nThe value of math_LOG10E is approximately the reciprocal of the value of math_LN10.\n
\n
",
+ "meta": "const"
+ },
+ "math_PI": {
+ "title": "math_PI:number",
+ "description": "math_PI:number
\n The Number value for π, the ratio of the circumference of a circle to its diameter, \nwhich is approximately 3.1415926535897932.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT1_2": {
+ "title": "math_SQRT1_2:number",
+ "description": "math_SQRT1_2:number
\n The Number value for the square root of 0.5, which is approximately 0.7071067811865476.\n
NOTE:\nThe value of math_SQRT1_2 is approximately the reciprocal of the value of math_SQRT2.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT2": {
+ "title": "math_SQRT2:number",
+ "description": "math_SQRT2:number
\n The Number value for the square root of 2, which is approximately 1.4142135623730951.\n
\n
",
+ "meta": "const"
+ },
+ "NaN": {
+ "title": "NaN:number",
+ "description": "",
+ "meta": "const"
+ },
+ "undefined": {
+ "title": "undefined:undefined",
+ "description": "",
+ "meta": "const"
+ },
+ "accumulate": {
+ "title": "accumulate(f, initial, xs) \u2192 {value}",
+ "description": "accumulate(f, initial, xs) → {value}
\n Applies binary\nfunction f
to the elements of xs
from\nright-to-left order, first applying f
to the last element\nand the value initial
, resulting in r
1,\nthen to the \nsecond-last element and r
1, resulting in\nr
2,\netc, and finally\nto the first element and r
n-1, where\nn
is the length of the\nlist. Thus, accumulate(f,zero,list(1,2,3))
results in\nf(1, f(2, f(3, zero)))
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
\nassuming f
takes constant time.\n
\n
",
+ "meta": "func"
+ },
+ "append": {
+ "title": "append(xs, ys) \u2192 {list}",
+ "description": "append(xs, ys) → {list}
\n Returns a list that results from \nappending the list ys
to the list xs
.\nRecursive process; time: O(n)
, space:\nO(n)
, where n
is the length of xs
.\nIn the result, null at the end of the first argument list\nis replaced by the second argument, regardless what the second\nargument consists of.\n
\n
",
+ "meta": "func"
+ },
+ "array_length": {
+ "title": "array_length(x) \u2192 {number}",
+ "description": "array_length(x) → {number}
\n returns\nthe current length of array x
, which is 1 plus the\nhighest index that has been used so far in an array assignment on \nx
. Here literal array expressions are counted too: The\narray [10, 20, 30]
has a length of 3.\n
\n
",
+ "meta": "func"
+ },
+ "build_list": {
+ "title": "build_list(n, f) \u2192 {list}",
+ "description": "build_list(n, f) → {list}
\n Makes a list with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nRecursive process; time: O(n)
, space: O(n)
.\n
\n
",
+ "meta": "func"
+ },
+ "build_stream": {
+ "title": "build_stream(n, f) \u2192 {stream}",
+ "description": "build_stream(n, f) → {stream}
\n Makes a stream with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nLazy? Yes: The result stream forces the application of f
\n for the next element\n
\n
",
+ "meta": "func"
+ },
+ "clear": {
+ "title": "clear(x) \u2192 {undefined}",
+ "description": "clear(x) → {undefined}
\n Sets the head of the array x
to\nfalse
. Returns undefined
.\nThis is an atomic operation.\n
\n
",
+ "meta": "func"
+ },
+ "concurrent_execute": {
+ "title": "concurrent_execute() \u2192 {undefined}",
+ "description": "concurrent_execute() → {undefined}
\n Setup multiple threads for concurrent execution. For each\nnullary function f_i
that returns undefined
,\nsetup a thread t_i
that executes the code in the body of\nf_i
. The thread that called concurrent_execute
\nalso executes concurrently with all t_i
. Returns\nundefined
. This is an atomic operation.\n
\n
",
+ "meta": "func"
+ },
+ "display": {
+ "title": "display(v, s) \u2192 {value}",
+ "description": "display(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console. The notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "draw_data": {
+ "title": "draw_data(x) \u2192 {value}",
+ "description": "draw_data(x) → {value}
\n visualizes x
in a separate drawing\narea in the Source Academy using a box-and-pointer diagram; time, space:\nO(n), where n is the number of data structures such as\npairs in x
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_list": {
+ "title": "enum_list(start, end) \u2192 {list}",
+ "description": "enum_list(start, end) → {list}
\n Returns a list that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_stream": {
+ "title": "enum_stream(start, end) \u2192 {stream}",
+ "description": "enum_stream(start, end) → {stream}
\n Returns a stream that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nLazy? Yes: The result stream forces the construction of\n each next element\n
\n
",
+ "meta": "func"
+ },
+ "equal": {
+ "title": "equal(x, y) \u2192 {boolean}",
+ "description": "equal(x, y) → {boolean}
\n Returns true
if both\nhave the same structure with respect to pair
,\nand the same numbers, boolean values, functions or empty list\nat corresponding leave positions (places that are not themselves pairs),\nand false
otherwise; time, space:\nO(n)
, where n
is the number of pairs in\nx
.\n
\n
",
+ "meta": "func"
+ },
+ "error": {
+ "title": "error(v, s) \u2192 {value}",
+ "description": "error(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console with error flag. \nThe evaluation\nof any call of
error
aborts the running program immediately.\nThe notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "eval_stream": {
+ "title": "eval_stream(s, n) \u2192 {list}",
+ "description": "eval_stream(s, n) → {list}
\n Constructs the list of the first n
elements\nof a given stream s
\nLazy? Sort-of: eval_stream
only forces the computation of\nthe first n
elements, and leaves the rest of\nthe stream untouched.\n
\n
",
+ "meta": "func"
+ },
+ "filter": {
+ "title": "filter(pred, xs) \u2192 {list}",
+ "description": "filter(pred, xs) → {list}
\n Returns a list that contains\nonly those elements for which the one-argument function\npred
\nreturns true
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "for_each": {
+ "title": "for_each(f, xs) \u2192 {boolean}",
+ "description": "for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the list xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nfor_each(fun, list(1, 2))
results in the calls\nfun(1)
and fun(2)
.\n
\n
",
+ "meta": "func"
+ },
+ "head": {
+ "title": "head(p) \u2192 {value}",
+ "description": "head(p) → {value}
\n returns head (first component) of given pair p
\n
\n
",
+ "meta": "func"
+ },
+ "integers_from": {
+ "title": "integers_from(start) \u2192 {stream}",
+ "description": "integers_from(start) → {stream}
\n Returns infinite stream if integers starting \nat given number n
using a step size of 1.\nLazy? Yes: The result stream forces the construction of\n each next element\n
\n
",
+ "meta": "func"
+ },
+ "is_array": {
+ "title": "is_array(x) \u2192 {boolean}",
+ "description": "is_array(x) → {boolean}
\n returns true
if x
\nis an array, and false
if it is not.\n
\n
",
+ "meta": "func"
+ },
+ "is_boolean": {
+ "title": "is_boolean(v) \u2192 {boolean}",
+ "description": "is_boolean(v) → {boolean}
\n checks whether a given value is a boolean\n
\n
",
+ "meta": "func"
+ },
+ "is_function": {
+ "title": "is_function(v) \u2192 {boolean}",
+ "description": "is_function(v) → {boolean}
\n checks whether a given value is a function\n
\n
",
+ "meta": "func"
+ },
+ "is_list": {
+ "title": "is_list(xs) \u2192 {xs}",
+ "description": "is_list(xs) → {xs}
\n Returns true
if\nxs
is a list as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of tail
operations that can be applied to xs
.\nrecurses down the list and checks that it ends with the empty list null\n
\n
",
+ "meta": "func"
+ },
+ "is_null": {
+ "title": "is_null(x) \u2192 {boolean}",
+ "description": "is_null(x) → {boolean}
\n returns true
if x
is the\nempty list null
, and false
otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_number": {
+ "title": "is_number(v) \u2192 {boolean}",
+ "description": "is_number(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_pair": {
+ "title": "is_pair(x) \u2192 {boolean}",
+ "description": "is_pair(x) → {boolean}
\n returns true
if x
is a\npair and false otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_stream": {
+ "title": "is_stream(xs) \u2192 {boolean}",
+ "description": "is_stream(xs) → {boolean}
\n Returns true
if\nxs
is a stream as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of stream_tail
operations that can be applied to xs
.\nrecurses down the stream and checks that it ends with the empty stream null.\nLaziness: No: is_stream
needs to force the given stream.\n
\n
",
+ "meta": "func"
+ },
+ "is_string": {
+ "title": "is_string(v) \u2192 {boolean}",
+ "description": "is_string(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_undefined": {
+ "title": "is_undefined(v) \u2192 {boolean}",
+ "description": "is_undefined(v) → {boolean}
\n checks whether a given value is the special value undefined
\n
\n
",
+ "meta": "func"
+ },
+ "length": {
+ "title": "length(xs) \u2192 {number}",
+ "description": "length(xs) → {number}
\n Returns the length of the list\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list": {
+ "title": "list() \u2192 {list}",
+ "description": "list() → {list}
\n Given n
values, returns a list of length n
.\nThe elements of the list are the given values in the given order.\n
\n
",
+ "meta": "func"
+ },
+ "list_ref": {
+ "title": "list_ref(xs, n) \u2192 {value}",
+ "description": "list_ref(xs, n) → {value}
\n Returns the element\nof list xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_stream": {
+ "title": "list_to_stream(xs) \u2192 {stream}",
+ "description": "list_to_stream(xs) → {stream}
\n Given list xs
, returns a stream of same length with\nthe same elements as xs
in the same order.\nLaziness: Yes: list_to_stream
\ngoes down the list only when forced.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_string": {
+ "title": "list_to_string(xs) \u2192 {string}",
+ "description": "list_to_string(xs) → {string}
\n Returns a string that represents\nlist xs
using the text-based box-and-pointer notation\n[...]
.\n
\n
",
+ "meta": "func"
+ },
+ "map": {
+ "title": "map(f, xs) \u2192 {list}",
+ "description": "map(f, xs) → {list}
\n Returns a list that results from list\nxs
by element-wise application of unary function f
. \nRecursive process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nf
is applied element-by-element:\nmap(f, list(1, 2))
results in list(f(1), f(2))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_abs": {
+ "title": "math_abs(x) \u2192 {number}",
+ "description": "math_abs(x) → {number}
\n computes the absolute value of x; the result has the same magnitude as x
but has positive sign.\n
\n
",
+ "meta": "func"
+ },
+ "math_acos": {
+ "title": "math_acos(x) \u2192 {number}",
+ "description": "math_acos(x) → {number}
\n computes the arc cosine of x
. \nThe result is expressed in radians and ranges from +0 to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_acosh": {
+ "title": "math_acosh(x) \u2192 {number}",
+ "description": "math_acosh(x) → {number}
\n computes the inverse hyperbolic cosine of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_asin": {
+ "title": "math_asin(x) \u2192 {number}",
+ "description": "math_asin(x) → {number}
\n computes the arc sine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_asinh": {
+ "title": "math_asinh(x) \u2192 {number}",
+ "description": "math_asinh(x) → {number}
\n computes the inverse hyperbolic \nsine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan": {
+ "title": "math_atan(x) \u2192 {number}",
+ "description": "math_atan(x) → {number}
\n computes the arc tangent of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan2": {
+ "title": "math_atan2(y, x) \u2192 {number}",
+ "description": "math_atan2(y, x) → {number}
\n computes the arc tangent of the quotient y
/ x
of the arguments y
and x
, where the signs of y
and x
are used to determine the quadrant of the result. Note that it is intentional and traditional for the two-argument arc tangent function that the argument named y
be first and the argument named x
be second. The result is expressed in radians and ranges from -π to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_atanh": {
+ "title": "math_atanh(x) \u2192 {number}",
+ "description": "math_atanh(x) → {number}
\n computes the inverse hyperbolic tangent of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_cbrt": {
+ "title": "math_cbrt(x) \u2192 {number}",
+ "description": "math_cbrt(x) → {number}
\n computes the cube root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_ceil": {
+ "title": "math_ceil(x) \u2192 {number}",
+ "description": "math_ceil(x) → {number}
\n computes the smallest (closest to -∞) Number value that is not less than x
and is an integer. If x
is already an integer, the result is x
.\nThe value of math_ceil(x) is the same as the value of -math_floor(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_clz32": {
+ "title": "math_clz32(n) \u2192 {number}",
+ "description": "math_clz32(n) → {number}
\n When math_clz32 is called with one argument
x
, the following steps are taken:\nLet n be ToUint32(x).\nLet p be the number of leading zero bits in the 32-bit binary representation of n.\nReturn p.\n
NOTE:\n
If n is 0, p will be 32. If the most significant bit of the 32-bit binary encoding of n is 1, \np will be 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_cos": {
+ "title": "math_cos(x) \u2192 {number}",
+ "description": "math_cos(x) → {number}
\n Computes the cosine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_cosh": {
+ "title": "math_cosh(x) \u2192 {number}",
+ "description": "math_cosh(x) → {number}
\n computes the hyperbolic cosine of
x
.\n
NOTE:\nThe value of cosh(x) is the same as (exp(x) + exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_exp": {
+ "title": "math_exp(x) \u2192 {number}",
+ "description": "math_exp(x) → {number}
\n computes the exponential function of x
\n(e raised to the power of x
, where e is the base of the natural logarithms).\n
\n
",
+ "meta": "func"
+ },
+ "math_expm1": {
+ "title": "math_expm1(x) \u2192 {number}",
+ "description": "math_expm1(x) → {number}
\n computes subtracting 1 from the \nexponential function of x
(e raised to the power of x
, where e is the base of \nthe natural logarithms). The result is computed in a way that is accurate even \nwhen the value of x
is close 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_floor": {
+ "title": "math_floor(x) \u2192 {number}",
+ "description": "math_floor(x) → {number}
\n computes the greatest (closest to +∞) Number value that is not greater than
x
\nand is an integer. \n
If
x
is already an integer, the result is
x
.\n
NOTE:\nThe value of math_floor(x) is the same as the value of -math_ceil(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_fround": {
+ "title": "math_fround(x) \u2192 {number}",
+ "description": "math_fround(x) → {number}
\n When math_fround is called with argument
x
, the following steps are taken:\n
- If
x
is NaN, return NaN. \n- If
x
is one of +0, -0, +∞, -∞, return x
. \n- Let x32 be the result of converting
x
to a value in IEEE 754-2008 binary32 format using roundTiesToEven mode. \n- Let x64 be the result of converting x32 to a value in IEEE 754-2008 binary64 format.
\n- Return the ECMAScript Number value corresponding to x64.
\n
\n
",
+ "meta": "func"
+ },
+ "math_hypot": {
+ "title": "math_hypot() \u2192 {number}",
+ "description": "math_hypot() → {number}
\n computes the square root\nof the sum of squares of its arguments.\n
If no arguments are passed, the result is +0.\n
\n
",
+ "meta": "func"
+ },
+ "math_imul": {
+ "title": "math_imul(x, x) \u2192 {number}",
+ "description": "math_imul(x, x) → {number}
\n When math_imul is called with arguments
x
and
y
,\nthe following steps are taken:\n
\n- Let a be ToUint32(x).
\n- Let b be ToUint32(y).
\n- Let product be (a × b) modulo 232.
\n- If product ≥ 231, return product - 232; otherwise return product.
\n
\n
",
+ "meta": "func"
+ },
+ "math_log": {
+ "title": "math_log(x) \u2192 {number}",
+ "description": "math_log(x) → {number}
\n Computes the natural logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log1p": {
+ "title": "math_log1p(x) \u2192 {number}",
+ "description": "math_log1p(x) → {number}
\n computes the natural logarithm of 1 + x
. The result is computed in a way that is accurate even when the value of x
is close to zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_log2": {
+ "title": "math_log2(x) \u2192 {number}",
+ "description": "math_log2(x) → {number}
\n computes the base 2 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log10": {
+ "title": "math_log10(x) \u2192 {number}",
+ "description": "math_log10(x) → {number}
\n computes the base 10 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_max": {
+ "title": "math_max() \u2192 {number}",
+ "description": "math_max() → {number}
\n Given zero or more numbers, returns the largest of them.\n
If no arguments are given, the result is -∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the largest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_min": {
+ "title": "math_min() \u2192 {number}",
+ "description": "math_min() → {number}
\n Given zero or more arguments, returns the smallest of them.\n
If no arguments are given, the result is +∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the smallest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_pow": {
+ "title": "math_pow(base, exponent) \u2192 {number}",
+ "description": "math_pow(base, exponent) → {number}
\n Computes the result of raising base to \nthe power of exponent.\n
\n
",
+ "meta": "func"
+ },
+ "math_random": {
+ "title": "math_random() \u2192 {number}",
+ "description": "math_random() → {number}
\n Returns a number value with positive sign, greater than or equal to 0 but less than 1, \nchosen randomly or pseudo randomly with approximately uniform distribution over that \nrange, using an implementation-dependent algorithm or strategy. This function takes no arguments.\nEach math_random function created for distinct realms must produce a distinct sequence \nof values from successive calls.\n
\n
",
+ "meta": "func"
+ },
+ "math_round": {
+ "title": "math_round(x) \u2192 {number}",
+ "description": "math_round(x) → {number}
\n Returns the number value that is closest to x
and is an integer. \n
If two integers are equally close to x
, then the result is the Number value \nthat is closer to +∞. If x
is already an integer, the result is x
.\nNOTE 1:\nmath_round(3.5) returns 4, but math_round(-3.5) returns -3.\n
\n
",
+ "meta": "func"
+ },
+ "math_sign": {
+ "title": "math_sign(x) \u2192 {number}",
+ "description": "math_sign(x) → {number}
\n Computes the sign of x
, indicating whether x
is positive, negative, or zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_sin": {
+ "title": "math_sin(x) \u2192 {number}",
+ "description": "math_sin(x) → {number}
\n Computes the sine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_sinh": {
+ "title": "math_sinh(x) \u2192 {number}",
+ "description": "math_sinh(x) → {number}
\n Computes the hyperbolic sine of
x
.\n
NOTE:\nThe value of sinh(x) is the same as (exp(x) - exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_sqrt": {
+ "title": "math_sqrt(x) \u2192 {number}",
+ "description": "math_sqrt(x) → {number}
\n Computes the square root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_tan": {
+ "title": "math_tan(x) \u2192 {number}",
+ "description": "math_tan(x) → {number}
\n Computes the tangent of x
. The argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_tanh": {
+ "title": "math_tanh(x) \u2192 {number}",
+ "description": "math_tanh(x) → {number}
\n Computes the hyperbolic tangent of
x
.\n
NOTE:\nThe value of
math_tanh(x)
is the same as\n
(exp(x) - exp(-x))/(exp(x) + exp(-x))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_trunc": {
+ "title": "math_trunc(x) \u2192 {number}",
+ "description": "math_trunc(x) → {number}
\n Computes the integral part of the number x
,\nremoving any fractional digits.\n
\n
",
+ "meta": "func"
+ },
+ "member": {
+ "title": "member(v, xs) \u2192 {list}",
+ "description": "member(v, xs) → {list}
\n Returns first postfix sublist\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the list.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "pair": {
+ "title": "pair(x, y) \u2192 {pair}",
+ "description": "pair(x, y) → {pair}
\n makes a pair whose head (first component) is x
\nand whose tail (second component) is y
.\n
\n
",
+ "meta": "func"
+ },
+ "parse_int": {
+ "title": "parse_int(s, i) \u2192 {number}",
+ "description": "parse_int(s, i) → {number}
\n Interprets a given string
s
as an integer, \nusing the positive integer
i
as radix, \nand returns the respective value.\n
Examples:
parse_int(\"909\", 10)
returns the number \n
909
, and
parse_int(\"-1111\", 2)
returns the number \n
-15
.
\nSee
ECMAScript Specification, Section 18.2.5 for details.\n
\n
",
+ "meta": "func"
+ },
+ "prompt": {
+ "title": "prompt(s) \u2192 {string}",
+ "description": "prompt(s) → {string}
\n Pops up a window that displays the string s
, provides\nan input line for the user to enter a text, a Cancel
button and an OK
button. \nThe call of prompt
\nsuspends execution of the program until one of the two buttons is pressed. If \nthe OK
button is pressed, prompt
returns the entered text as a string.\nIf the Cancel
button is pressed, prompt
returns a non-string value.\n
\n
",
+ "meta": "func"
+ },
+ "remove": {
+ "title": "remove(v, xs) \u2192 {list}",
+ "description": "remove(v, xs) → {list}
\n Returns a list that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. Recursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "remove_all": {
+ "title": "remove_all(v, xs) \u2192 {list}",
+ "description": "remove_all(v, xs) → {list}
\n Returns a list that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. \nRecursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "reverse": {
+ "title": "reverse(xs) \u2192 {list}",
+ "description": "reverse(xs) → {list}
\n Returns list xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result list.\n
\n
",
+ "meta": "func"
+ },
+ "runtime": {
+ "title": "runtime() \u2192 {number}",
+ "description": "runtime() → {number}
\n Returns number of milliseconds elapsed since January 1, 1970 00:00:00 UTC.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "set_head": {
+ "title": "set_head(p, x) \u2192 {undefined}",
+ "description": "set_head(p, x) → {undefined}
\n changes the pair p
such that its head is x
.\n
\n
",
+ "meta": "func"
+ },
+ "set_tail": {
+ "title": "set_tail(p, x) \u2192 {undefined}",
+ "description": "set_tail(p, x) → {undefined}
\n changes the pair p
such that its tail is x
.\n
\n
",
+ "meta": "func"
+ },
+ "stream": {
+ "title": "stream() \u2192 {stream}",
+ "description": "stream() → {stream}
\n Given n
values, returns a stream of length n
.\nThe elements of the stream are the given values in the given order.\nLazy? No: A\ncomplete list is generated, \nand then a stream using list_to_stream
is generated from it.\n
\n
",
+ "meta": "func"
+ },
+ "stream_append": {
+ "title": "stream_append(xs, ys) \u2192 {stream}",
+ "description": "stream_append(xs, ys) → {stream}
\n Returns a stream that results from \nappending the stream ys
to the stream xs
.\nIn the result, null at the end of the first argument stream\nis replaced by the second argument, regardless what the second\nargument consists of.\nLazy? Yes: the result stream forces the actual append operation\n
\n
",
+ "meta": "func"
+ },
+ "stream_filter": {
+ "title": "stream_filter(pred, xs) \u2192 {stream}",
+ "description": "stream_filter(pred, xs) → {stream}
\n Returns a stream that contains\nonly those elements of given stream xs
\nfor which the one-argument function\npred
\nreturns true
.\nLazy? Yes: The result stream forces the construction of\n each next element. Of course, the construction\n of the next element needs to go down the stream\n until an element is found for which pred
holds.\n
\n
",
+ "meta": "func"
+ },
+ "stream_for_each": {
+ "title": "stream_for_each(f, xs) \u2192 {boolean}",
+ "description": "stream_for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the stream xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nstream_for_each(f, stream(1, 2))
results in the calls\nf(1)
and f(2)
.\nLazy? No: stream_for_each
\nforces the exploration of the entire stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_length": {
+ "title": "stream_length(xs) \u2192 {number}",
+ "description": "stream_length(xs) → {number}
\n Returns the length of the stream\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\nLazy? No: The function needs to explore the whole stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_map": {
+ "title": "stream_map(f, xs) \u2192 {stream}",
+ "description": "stream_map(f, xs) → {stream}
\n Returns a stream that results from stream\nxs
by element-wise application \nof unary function f
. \nf
is applied element-by-element:\nstream_map(f, stream(1,2))
results in\nthe same as stream(f(1),f(2))
.\nLazy? Yes: The argument stream is only explored as forced by\n the result stream.\n
\n
",
+ "meta": "func"
+ },
+ "stream_member": {
+ "title": "stream_member(v, xs) \u2192 {stream}",
+ "description": "stream_member(v, xs) → {stream}
\n Returns first postfix substream\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the stream.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\nLazy? Sort-of: stream_member
\nforces the stream only until the element \nis found.\n
\n
",
+ "meta": "func"
+ },
+ "stream_ref": {
+ "title": "stream_ref(xs, n) \u2192 {value}",
+ "description": "stream_ref(xs, n) → {value}
\n Returns the element\nof stream xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\nLazy? Sort-of: stream_ref
only forces the computation of\n the first n
elements, and leaves the rest of\n the stream untouched.\n
\n
",
+ "meta": "func"
+ },
+ "stream_remove": {
+ "title": "stream_remove(v, xs) \u2192 {stream}",
+ "description": "stream_remove(v, xs) → {stream}
\n Returns a stream that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nstream if there is no occurrence. \nLazy? Yes: the result stream forces the construction of each next element\n
\n
",
+ "meta": "func"
+ },
+ "stream_remove_all": {
+ "title": "stream_remove_all(v, xs) \u2192 {stream}",
+ "description": "stream_remove_all(v, xs) → {stream}
\n Returns a stream that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nstream if there is no occurrence. \nRecursive process.\nLazy? Yes: the result stream forces the construction of each next \nelement\n
\n
",
+ "meta": "func"
+ },
+ "stream_reverse": {
+ "title": "stream_reverse(xs) \u2192 {stream}",
+ "description": "stream_reverse(xs) → {stream}
\n Returns stream xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result stream.\nLazy? No: stream_reverse
\nforces the exploration of the entire stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_tail": {
+ "title": "stream_tail(xs) \u2192 {Stream}",
+ "description": "stream_tail(xs) → {Stream}
\n assumes that the tail (second component) of the\npair {x} is a nullary function, and returns the result of\napplying that function. Throws an exception if the argument \nis not a pair, or if the tail is not a function.\nLaziness: Yes: {stream_tail} only forces the direct tail \nstream, but not the rest of the stream, i.e. not the tail \nof the tail, etc.\n
\n
",
+ "meta": "func"
+ },
+ "stream_to_list": {
+ "title": "stream_to_list(xs) \u2192 {list}",
+ "description": "stream_to_list(xs) → {list}
\n Given stream xs
, returns a list of same length with\nthe same elements as xs
in the same order.\nLaziness: No: stream_to_list
needs to force the whole \nstream.\n
\n
",
+ "meta": "func"
+ },
+ "stringify": {
+ "title": "stringify(v) \u2192 {string}",
+ "description": "stringify(v) → {string}
\n returns a string that represents the value
v
, using a\nnotation that is is consistent with \n
JSON, \nbut also displays
undefined
and function objects.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "tail": {
+ "title": "tail(p) \u2192 {value}",
+ "description": "tail(p) → {value}
\n returns tail (second component of given pair p
\n
\n
",
+ "meta": "func"
+ },
+ "test_and_set": {
+ "title": "test_and_set(x) \u2192 {value}",
+ "description": "test_and_set(x) → {value}
\n Returns the head of the array x
, and sets the\nhead of x
to true
. Assumes the\nhead of the array x
is a boolean.\nThis is an atomic operation.\n
\n
",
+ "meta": "func"
+ }
+}
\ No newline at end of file
diff --git a/src/editors/ace/docTooltip/source_4.json b/src/editors/ace/docTooltip/source_4.json
new file mode 100644
index 000000000..42ec62b4e
--- /dev/null
+++ b/src/editors/ace/docTooltip/source_4.json
@@ -0,0 +1,522 @@
+{
+ "Infinity": {
+ "title": "Infinity:number",
+ "description": "",
+ "meta": "const"
+ },
+ "math_LN2": {
+ "title": "math_LN2:number",
+ "description": "math_LN2:number
\n The Number value for the natural logarithm of 2, \nwhich is approximately 0.6931471805599453.\n
\n
",
+ "meta": "const"
+ },
+ "math_LN10": {
+ "title": "math_LN10:number",
+ "description": "math_LN10:number
\n The Number value for the natural logarithm of 10, \nwhich is approximately 2.302585092994046.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG2E": {
+ "title": "math_LOG2E:number",
+ "description": "math_LOG2E:number
\n The Number value for the base-2 logarithm of eℝ, the base of the natural logarithms; \nthis value is approximately 1.4426950408889634.\n
NOTE:\nThe value of math_LOG2E is approximately the reciprocal of the value of math_LN2.\n
\n
",
+ "meta": "const"
+ },
+ "math_LOG10E": {
+ "title": "math_LOG10E:number",
+ "description": "math_LOG10E:number
\n The Number value for the base-10 logarithm of e, \nthe base of the natural logarithms; this value is approximately 0.4342944819032518.\n
NOTE:\nThe value of math_LOG10E is approximately the reciprocal of the value of math_LN10.\n
\n
",
+ "meta": "const"
+ },
+ "math_PI": {
+ "title": "math_PI:number",
+ "description": "math_PI:number
\n The Number value for π, the ratio of the circumference of a circle to its diameter, \nwhich is approximately 3.1415926535897932.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT1_2": {
+ "title": "math_SQRT1_2:number",
+ "description": "math_SQRT1_2:number
\n The Number value for the square root of 0.5, which is approximately 0.7071067811865476.\n
NOTE:\nThe value of math_SQRT1_2 is approximately the reciprocal of the value of math_SQRT2.\n
\n
",
+ "meta": "const"
+ },
+ "math_SQRT2": {
+ "title": "math_SQRT2:number",
+ "description": "math_SQRT2:number
\n The Number value for the square root of 2, which is approximately 1.4142135623730951.\n
\n
",
+ "meta": "const"
+ },
+ "NaN": {
+ "title": "NaN:number",
+ "description": "",
+ "meta": "const"
+ },
+ "undefined": {
+ "title": "undefined:undefined",
+ "description": "",
+ "meta": "const"
+ },
+ "accumulate": {
+ "title": "accumulate(f, initial, xs) \u2192 {value}",
+ "description": "accumulate(f, initial, xs) → {value}
\n Applies binary\nfunction f
to the elements of xs
from\nright-to-left order, first applying f
to the last element\nand the value initial
, resulting in r
1,\nthen to the \nsecond-last element and r
1, resulting in\nr
2,\netc, and finally\nto the first element and r
n-1, where\nn
is the length of the\nlist. Thus, accumulate(f,zero,list(1,2,3))
results in\nf(1, f(2, f(3, zero)))
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
\nassuming f
takes constant time.\n
\n
",
+ "meta": "func"
+ },
+ "append": {
+ "title": "append(xs, ys) \u2192 {list}",
+ "description": "append(xs, ys) → {list}
\n Returns a list that results from \nappending the list ys
to the list xs
.\nRecursive process; time: O(n)
, space:\nO(n)
, where n
is the length of xs
.\nIn the result, null at the end of the first argument list\nis replaced by the second argument, regardless what the second\nargument consists of.\n
\n
",
+ "meta": "func"
+ },
+ "apply_in_underlying_javascript": {
+ "title": "apply_in_underlying_javascript(f, xs) \u2192 {boolean}",
+ "description": "apply_in_underlying_javascript(f, xs) → {boolean}
\n calls the function
f
\nwith arguments given in list
xs
. For example:
function times(x, y) {\nreturn x * y;\n}\napply_in_underlying_javascript(times, list(2, 3)); // returns 6
\n
\n
",
+ "meta": "func"
+ },
+ "array_length": {
+ "title": "array_length(x) \u2192 {number}",
+ "description": "array_length(x) → {number}
\n returns\nthe current length of array x
, which is 1 plus the\nhighest index that has been used so far in an array assignment on \nx
. Here literal array expressions are counted too: The\narray [10, 20, 30]
has a length of 3.\n
\n
",
+ "meta": "func"
+ },
+ "build_list": {
+ "title": "build_list(n, f) \u2192 {list}",
+ "description": "build_list(n, f) → {list}
\n Makes a list with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nRecursive process; time: O(n)
, space: O(n)
.\n
\n
",
+ "meta": "func"
+ },
+ "build_stream": {
+ "title": "build_stream(n, f) \u2192 {stream}",
+ "description": "build_stream(n, f) → {stream}
\n Makes a stream with n
\nelements by applying the unary function f
\nto the numbers 0 to n - 1
, assumed to be a non-negative integer.\nLazy? Yes: The result stream forces the application of f
\n for the next element\n
\n
",
+ "meta": "func"
+ },
+ "display": {
+ "title": "display(v, s) \u2192 {value}",
+ "description": "display(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console. The notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "draw_data": {
+ "title": "draw_data(x) \u2192 {value}",
+ "description": "draw_data(x) → {value}
\n visualizes x
in a separate drawing\narea in the Source Academy using a box-and-pointer diagram; time, space:\nO(n), where n is the number of data structures such as\npairs in x
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_list": {
+ "title": "enum_list(start, end) \u2192 {list}",
+ "description": "enum_list(start, end) → {list}
\n Returns a list that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "enum_stream": {
+ "title": "enum_stream(start, end) \u2192 {stream}",
+ "description": "enum_stream(start, end) → {stream}
\n Returns a stream that enumerates\nnumbers starting from start
using a step size of 1, until\nthe number exceeds (>
) end
.\nLazy? Yes: The result stream forces the construction of\n each next element\n
\n
",
+ "meta": "func"
+ },
+ "equal": {
+ "title": "equal(x, y) \u2192 {boolean}",
+ "description": "equal(x, y) → {boolean}
\n Returns true
if both\nhave the same structure with respect to pair
,\nand the same numbers, boolean values, functions or empty list\nat corresponding leave positions (places that are not themselves pairs),\nand false
otherwise; time, space:\nO(n)
, where n
is the number of pairs in\nx
.\n
\n
",
+ "meta": "func"
+ },
+ "error": {
+ "title": "error(v, s) \u2192 {value}",
+ "description": "error(v, s) → {value}
\n Displays the given string
s
, followed by a space character, followed by the\nvalue
v
in the console with error flag. \nThe evaluation\nof any call of
error
aborts the running program immediately.\nThe notation used for the display of values \nis consistent with \n
JSON, \nbut also displays
undefined
and function objects.\n
\n
",
+ "meta": "func"
+ },
+ "eval_stream": {
+ "title": "eval_stream(s, n) \u2192 {list}",
+ "description": "eval_stream(s, n) → {list}
\n Constructs the list of the first n
elements\nof a given stream s
\nLazy? Sort-of: eval_stream
only forces the computation of\nthe first n
elements, and leaves the rest of\nthe stream untouched.\n
\n
",
+ "meta": "func"
+ },
+ "filter": {
+ "title": "filter(pred, xs) \u2192 {list}",
+ "description": "filter(pred, xs) → {list}
\n Returns a list that contains\nonly those elements for which the one-argument function\npred
\nreturns true
.\nRecursive process;\ntime: O(n)
, space: O(n)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "for_each": {
+ "title": "for_each(f, xs) \u2192 {boolean}",
+ "description": "for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the list xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nfor_each(fun, list(1, 2))
results in the calls\nfun(1)
and fun(2)
.\n
\n
",
+ "meta": "func"
+ },
+ "head": {
+ "title": "head(p) \u2192 {value}",
+ "description": "head(p) → {value}
\n returns head (first component) of given pair p
\n
\n
",
+ "meta": "func"
+ },
+ "integers_from": {
+ "title": "integers_from(start) \u2192 {stream}",
+ "description": "integers_from(start) → {stream}
\n Returns infinite stream if integers starting \nat given number n
using a step size of 1.\nLazy? Yes: The result stream forces the construction of\n each next element\n
\n
",
+ "meta": "func"
+ },
+ "is_array": {
+ "title": "is_array(x) \u2192 {boolean}",
+ "description": "is_array(x) → {boolean}
\n returns true
if x
\nis an array, and false
if it is not.\n
\n
",
+ "meta": "func"
+ },
+ "is_boolean": {
+ "title": "is_boolean(v) \u2192 {boolean}",
+ "description": "is_boolean(v) → {boolean}
\n checks whether a given value is a boolean\n
\n
",
+ "meta": "func"
+ },
+ "is_function": {
+ "title": "is_function(v) \u2192 {boolean}",
+ "description": "is_function(v) → {boolean}
\n checks whether a given value is a function\n
\n
",
+ "meta": "func"
+ },
+ "is_list": {
+ "title": "is_list(xs) \u2192 {xs}",
+ "description": "is_list(xs) → {xs}
\n Returns true
if\nxs
is a list as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of tail
operations that can be applied to xs
.\nrecurses down the list and checks that it ends with the empty list null\n
\n
",
+ "meta": "func"
+ },
+ "is_null": {
+ "title": "is_null(x) \u2192 {boolean}",
+ "description": "is_null(x) → {boolean}
\n returns true
if x
is the\nempty list null
, and false
otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_number": {
+ "title": "is_number(v) \u2192 {boolean}",
+ "description": "is_number(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_pair": {
+ "title": "is_pair(x) \u2192 {boolean}",
+ "description": "is_pair(x) → {boolean}
\n returns true
if x
is a\npair and false otherwise.\n
\n
",
+ "meta": "func"
+ },
+ "is_stream": {
+ "title": "is_stream(xs) \u2192 {boolean}",
+ "description": "is_stream(xs) → {boolean}
\n Returns true
if\nxs
is a stream as defined in the textbook, and\nfalse
otherwise. Iterative process; \ntime: O(n)
, space: O(1)
, where n
\nis the length of the \nchain of stream_tail
operations that can be applied to xs
.\nrecurses down the stream and checks that it ends with the empty stream null.\nLaziness: No: is_stream
needs to force the given stream.\n
\n
",
+ "meta": "func"
+ },
+ "is_string": {
+ "title": "is_string(v) \u2192 {boolean}",
+ "description": "is_string(v) → {boolean}
\n
",
+ "meta": "func"
+ },
+ "is_undefined": {
+ "title": "is_undefined(v) \u2192 {boolean}",
+ "description": "is_undefined(v) → {boolean}
\n checks whether a given value is the special value undefined
\n
\n
",
+ "meta": "func"
+ },
+ "length": {
+ "title": "length(xs) \u2192 {number}",
+ "description": "length(xs) → {number}
\n Returns the length of the list\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list": {
+ "title": "list() \u2192 {list}",
+ "description": "list() → {list}
\n Given n
values, returns a list of length n
.\nThe elements of the list are the given values in the given order.\n
\n
",
+ "meta": "func"
+ },
+ "list_ref": {
+ "title": "list_ref(xs, n) \u2192 {value}",
+ "description": "list_ref(xs, n) → {value}
\n Returns the element\nof list xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_stream": {
+ "title": "list_to_stream(xs) \u2192 {stream}",
+ "description": "list_to_stream(xs) → {stream}
\n Given list xs
, returns a stream of same length with\nthe same elements as xs
in the same order.\nLaziness: Yes: list_to_stream
\ngoes down the list only when forced.\n
\n
",
+ "meta": "func"
+ },
+ "list_to_string": {
+ "title": "list_to_string(xs) \u2192 {string}",
+ "description": "list_to_string(xs) → {string}
\n Returns a string that represents\nlist xs
using the text-based box-and-pointer notation\n[...]
.\n
\n
",
+ "meta": "func"
+ },
+ "map": {
+ "title": "map(f, xs) \u2192 {list}",
+ "description": "map(f, xs) → {list}
\n Returns a list that results from list\nxs
by element-wise application of unary function f
. \nRecursive process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nf
is applied element-by-element:\nmap(f, list(1, 2))
results in list(f(1), f(2))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_abs": {
+ "title": "math_abs(x) \u2192 {number}",
+ "description": "math_abs(x) → {number}
\n computes the absolute value of x; the result has the same magnitude as x
but has positive sign.\n
\n
",
+ "meta": "func"
+ },
+ "math_acos": {
+ "title": "math_acos(x) \u2192 {number}",
+ "description": "math_acos(x) → {number}
\n computes the arc cosine of x
. \nThe result is expressed in radians and ranges from +0 to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_acosh": {
+ "title": "math_acosh(x) \u2192 {number}",
+ "description": "math_acosh(x) → {number}
\n computes the inverse hyperbolic cosine of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_asin": {
+ "title": "math_asin(x) \u2192 {number}",
+ "description": "math_asin(x) → {number}
\n computes the arc sine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_asinh": {
+ "title": "math_asinh(x) \u2192 {number}",
+ "description": "math_asinh(x) → {number}
\n computes the inverse hyperbolic \nsine of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan": {
+ "title": "math_atan(x) \u2192 {number}",
+ "description": "math_atan(x) → {number}
\n computes the arc tangent of x
. The result is expressed in radians and ranges from -π / 2 to +π / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_atan2": {
+ "title": "math_atan2(y, x) \u2192 {number}",
+ "description": "math_atan2(y, x) → {number}
\n computes the arc tangent of the quotient y
/ x
of the arguments y
and x
, where the signs of y
and x
are used to determine the quadrant of the result. Note that it is intentional and traditional for the two-argument arc tangent function that the argument named y
be first and the argument named x
be second. The result is expressed in radians and ranges from -π to +π.\n
\n
",
+ "meta": "func"
+ },
+ "math_atanh": {
+ "title": "math_atanh(x) \u2192 {number}",
+ "description": "math_atanh(x) → {number}
\n computes the inverse hyperbolic tangent of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_cbrt": {
+ "title": "math_cbrt(x) \u2192 {number}",
+ "description": "math_cbrt(x) → {number}
\n computes the cube root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_ceil": {
+ "title": "math_ceil(x) \u2192 {number}",
+ "description": "math_ceil(x) → {number}
\n computes the smallest (closest to -∞) Number value that is not less than x
and is an integer. If x
is already an integer, the result is x
.\nThe value of math_ceil(x) is the same as the value of -math_floor(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_clz32": {
+ "title": "math_clz32(n) \u2192 {number}",
+ "description": "math_clz32(n) → {number}
\n When math_clz32 is called with one argument
x
, the following steps are taken:\nLet n be ToUint32(x).\nLet p be the number of leading zero bits in the 32-bit binary representation of n.\nReturn p.\n
NOTE:\n
If n is 0, p will be 32. If the most significant bit of the 32-bit binary encoding of n is 1, \np will be 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_cos": {
+ "title": "math_cos(x) \u2192 {number}",
+ "description": "math_cos(x) → {number}
\n Computes the cosine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_cosh": {
+ "title": "math_cosh(x) \u2192 {number}",
+ "description": "math_cosh(x) → {number}
\n computes the hyperbolic cosine of
x
.\n
NOTE:\nThe value of cosh(x) is the same as (exp(x) + exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_exp": {
+ "title": "math_exp(x) \u2192 {number}",
+ "description": "math_exp(x) → {number}
\n computes the exponential function of x
\n(e raised to the power of x
, where e is the base of the natural logarithms).\n
\n
",
+ "meta": "func"
+ },
+ "math_expm1": {
+ "title": "math_expm1(x) \u2192 {number}",
+ "description": "math_expm1(x) → {number}
\n computes subtracting 1 from the \nexponential function of x
(e raised to the power of x
, where e is the base of \nthe natural logarithms). The result is computed in a way that is accurate even \nwhen the value of x
is close 0.\n
\n
",
+ "meta": "func"
+ },
+ "math_floor": {
+ "title": "math_floor(x) \u2192 {number}",
+ "description": "math_floor(x) → {number}
\n computes the greatest (closest to +∞) Number value that is not greater than
x
\nand is an integer. \n
If
x
is already an integer, the result is
x
.\n
NOTE:\nThe value of math_floor(x) is the same as the value of -math_ceil(-x).\n
\n
",
+ "meta": "func"
+ },
+ "math_fround": {
+ "title": "math_fround(x) \u2192 {number}",
+ "description": "math_fround(x) → {number}
\n When math_fround is called with argument
x
, the following steps are taken:\n
- If
x
is NaN, return NaN. \n- If
x
is one of +0, -0, +∞, -∞, return x
. \n- Let x32 be the result of converting
x
to a value in IEEE 754-2008 binary32 format using roundTiesToEven mode. \n- Let x64 be the result of converting x32 to a value in IEEE 754-2008 binary64 format.
\n- Return the ECMAScript Number value corresponding to x64.
\n
\n
",
+ "meta": "func"
+ },
+ "math_hypot": {
+ "title": "math_hypot() \u2192 {number}",
+ "description": "math_hypot() → {number}
\n computes the square root\nof the sum of squares of its arguments.\n
If no arguments are passed, the result is +0.\n
\n
",
+ "meta": "func"
+ },
+ "math_imul": {
+ "title": "math_imul(x, x) \u2192 {number}",
+ "description": "math_imul(x, x) → {number}
\n When math_imul is called with arguments
x
and
y
,\nthe following steps are taken:\n
\n- Let a be ToUint32(x).
\n- Let b be ToUint32(y).
\n- Let product be (a × b) modulo 232.
\n- If product ≥ 231, return product - 232; otherwise return product.
\n
\n
",
+ "meta": "func"
+ },
+ "math_log": {
+ "title": "math_log(x) \u2192 {number}",
+ "description": "math_log(x) → {number}
\n Computes the natural logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log1p": {
+ "title": "math_log1p(x) \u2192 {number}",
+ "description": "math_log1p(x) → {number}
\n computes the natural logarithm of 1 + x
. The result is computed in a way that is accurate even when the value of x
is close to zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_log2": {
+ "title": "math_log2(x) \u2192 {number}",
+ "description": "math_log2(x) → {number}
\n computes the base 2 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_log10": {
+ "title": "math_log10(x) \u2192 {number}",
+ "description": "math_log10(x) → {number}
\n computes the base 10 logarithm of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_max": {
+ "title": "math_max() \u2192 {number}",
+ "description": "math_max() → {number}
\n Given zero or more numbers, returns the largest of them.\n
If no arguments are given, the result is -∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the largest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_min": {
+ "title": "math_min() \u2192 {number}",
+ "description": "math_min() → {number}
\n Given zero or more arguments, returns the smallest of them.\n
If no arguments are given, the result is +∞.\n
If any value is NaN, the result is NaN.\nThe comparison of values to determine the smallest value is done using the \nAbstract Relational Comparison algorithm except that +0 is considered to be larger than -0.\n
\n
",
+ "meta": "func"
+ },
+ "math_pow": {
+ "title": "math_pow(base, exponent) \u2192 {number}",
+ "description": "math_pow(base, exponent) → {number}
\n Computes the result of raising base to \nthe power of exponent.\n
\n
",
+ "meta": "func"
+ },
+ "math_random": {
+ "title": "math_random() \u2192 {number}",
+ "description": "math_random() → {number}
\n Returns a number value with positive sign, greater than or equal to 0 but less than 1, \nchosen randomly or pseudo randomly with approximately uniform distribution over that \nrange, using an implementation-dependent algorithm or strategy. This function takes no arguments.\nEach math_random function created for distinct realms must produce a distinct sequence \nof values from successive calls.\n
\n
",
+ "meta": "func"
+ },
+ "math_round": {
+ "title": "math_round(x) \u2192 {number}",
+ "description": "math_round(x) → {number}
\n Returns the number value that is closest to x
and is an integer. \n
If two integers are equally close to x
, then the result is the Number value \nthat is closer to +∞. If x
is already an integer, the result is x
.\nNOTE 1:\nmath_round(3.5) returns 4, but math_round(-3.5) returns -3.\n
\n
",
+ "meta": "func"
+ },
+ "math_sign": {
+ "title": "math_sign(x) \u2192 {number}",
+ "description": "math_sign(x) → {number}
\n Computes the sign of x
, indicating whether x
is positive, negative, or zero.\n
\n
",
+ "meta": "func"
+ },
+ "math_sin": {
+ "title": "math_sin(x) \u2192 {number}",
+ "description": "math_sin(x) → {number}
\n Computes the sine of x
. \nThe argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_sinh": {
+ "title": "math_sinh(x) \u2192 {number}",
+ "description": "math_sinh(x) → {number}
\n Computes the hyperbolic sine of
x
.\n
NOTE:\nThe value of sinh(x) is the same as (exp(x) - exp(-x)) / 2.\n
\n
",
+ "meta": "func"
+ },
+ "math_sqrt": {
+ "title": "math_sqrt(x) \u2192 {number}",
+ "description": "math_sqrt(x) → {number}
\n Computes the square root of x
.\n
\n
",
+ "meta": "func"
+ },
+ "math_tan": {
+ "title": "math_tan(x) \u2192 {number}",
+ "description": "math_tan(x) → {number}
\n Computes the tangent of x
. The argument is expressed in radians.\n
\n
",
+ "meta": "func"
+ },
+ "math_tanh": {
+ "title": "math_tanh(x) \u2192 {number}",
+ "description": "math_tanh(x) → {number}
\n Computes the hyperbolic tangent of
x
.\n
NOTE:\nThe value of
math_tanh(x)
is the same as\n
(exp(x) - exp(-x))/(exp(x) + exp(-x))
.\n
\n
",
+ "meta": "func"
+ },
+ "math_trunc": {
+ "title": "math_trunc(x) \u2192 {number}",
+ "description": "math_trunc(x) → {number}
\n Computes the integral part of the number x
,\nremoving any fractional digits.\n
\n
",
+ "meta": "func"
+ },
+ "member": {
+ "title": "member(v, xs) \u2192 {list}",
+ "description": "member(v, xs) → {list}
\n Returns first postfix sublist\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the list.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "pair": {
+ "title": "pair(x, y) \u2192 {pair}",
+ "description": "pair(x, y) → {pair}
\n makes a pair whose head (first component) is x
\nand whose tail (second component) is y
.\n
\n
",
+ "meta": "func"
+ },
+ "parse": {
+ "title": "parse(x) \u2192 {value}",
+ "description": "",
+ "meta": "func"
+ },
+ "parse_int": {
+ "title": "parse_int(s, i) \u2192 {number}",
+ "description": "parse_int(s, i) → {number}
\n Interprets a given string
s
as an integer, \nusing the positive integer
i
as radix, \nand returns the respective value.\n
Examples:
parse_int(\"909\", 10)
returns the number \n
909
, and
parse_int(\"-1111\", 2)
returns the number \n
-15
.
\nSee
ECMAScript Specification, Section 18.2.5 for details.\n
\n
",
+ "meta": "func"
+ },
+ "prompt": {
+ "title": "prompt(s) \u2192 {string}",
+ "description": "prompt(s) → {string}
\n Pops up a window that displays the string s
, provides\nan input line for the user to enter a text, a Cancel
button and an OK
button. \nThe call of prompt
\nsuspends execution of the program until one of the two buttons is pressed. If \nthe OK
button is pressed, prompt
returns the entered text as a string.\nIf the Cancel
button is pressed, prompt
returns a non-string value.\n
\n
",
+ "meta": "func"
+ },
+ "remove": {
+ "title": "remove(v, xs) \u2192 {list}",
+ "description": "remove(v, xs) → {list}
\n Returns a list that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. Recursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "remove_all": {
+ "title": "remove_all(v, xs) \u2192 {list}",
+ "description": "remove_all(v, xs) → {list}
\n Returns a list that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nlist if there is no occurrence. \nRecursive process;\ntime: O(n)
, space: O(n)
, where n
\nis the length of xs
.\n
\n
",
+ "meta": "func"
+ },
+ "reverse": {
+ "title": "reverse(xs) \u2192 {list}",
+ "description": "reverse(xs) → {list}
\n Returns list xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result list.\n
\n
",
+ "meta": "func"
+ },
+ "runtime": {
+ "title": "runtime() \u2192 {number}",
+ "description": "runtime() → {number}
\n Returns number of milliseconds elapsed since January 1, 1970 00:00:00 UTC.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "set_head": {
+ "title": "set_head(p, x) \u2192 {undefined}",
+ "description": "set_head(p, x) → {undefined}
\n changes the pair p
such that its head is x
.\n
\n
",
+ "meta": "func"
+ },
+ "set_tail": {
+ "title": "set_tail(p, x) \u2192 {undefined}",
+ "description": "set_tail(p, x) → {undefined}
\n changes the pair p
such that its tail is x
.\n
\n
",
+ "meta": "func"
+ },
+ "stream": {
+ "title": "stream() \u2192 {stream}",
+ "description": "stream() → {stream}
\n Given n
values, returns a stream of length n
.\nThe elements of the stream are the given values in the given order.\nLazy? No: A\ncomplete list is generated, \nand then a stream using list_to_stream
is generated from it.\n
\n
",
+ "meta": "func"
+ },
+ "stream_append": {
+ "title": "stream_append(xs, ys) \u2192 {stream}",
+ "description": "stream_append(xs, ys) → {stream}
\n Returns a stream that results from \nappending the stream ys
to the stream xs
.\nIn the result, null at the end of the first argument stream\nis replaced by the second argument, regardless what the second\nargument consists of.\nLazy? Yes: the result stream forces the actual append operation\n
\n
",
+ "meta": "func"
+ },
+ "stream_filter": {
+ "title": "stream_filter(pred, xs) \u2192 {stream}",
+ "description": "stream_filter(pred, xs) → {stream}
\n Returns a stream that contains\nonly those elements of given stream xs
\nfor which the one-argument function\npred
\nreturns true
.\nLazy? Yes: The result stream forces the construction of\n each next element. Of course, the construction\n of the next element needs to go down the stream\n until an element is found for which pred
holds.\n
\n
",
+ "meta": "func"
+ },
+ "stream_for_each": {
+ "title": "stream_for_each(f, xs) \u2192 {boolean}",
+ "description": "stream_for_each(f, xs) → {boolean}
\n Applies unary function f
to every\nelement of the stream xs
.\nIterative process; time: O(n)
, space: O(1)
,\nWhere n
is the length of xs
.\nf
is applied element-by-element:\nstream_for_each(f, stream(1, 2))
results in the calls\nf(1)
and f(2)
.\nLazy? No: stream_for_each
\nforces the exploration of the entire stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_length": {
+ "title": "stream_length(xs) \u2192 {number}",
+ "description": "stream_length(xs) → {number}
\n Returns the length of the stream\nxs
. \nIterative process; time: O(n)
, space:\nO(1)
, where n
is the length of xs
.\nLazy? No: The function needs to explore the whole stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_map": {
+ "title": "stream_map(f, xs) \u2192 {stream}",
+ "description": "stream_map(f, xs) → {stream}
\n Returns a stream that results from stream\nxs
by element-wise application \nof unary function f
. \nf
is applied element-by-element:\nstream_map(f, stream(1,2))
results in\nthe same as stream(f(1),f(2))
.\nLazy? Yes: The argument stream is only explored as forced by\n the result stream.\n
\n
",
+ "meta": "func"
+ },
+ "stream_member": {
+ "title": "stream_member(v, xs) \u2192 {stream}",
+ "description": "stream_member(v, xs) → {stream}
\n Returns first postfix substream\nwhose head is identical to\nv
(using ===
); returns null
if the\nelement does not occur in the stream.\nIterative process; time: O(n)
,\nspace: O(1)
, where n
is the length of xs
.\nLazy? Sort-of: stream_member
\nforces the stream only until the element \nis found.\n
\n
",
+ "meta": "func"
+ },
+ "stream_ref": {
+ "title": "stream_ref(xs, n) \u2192 {value}",
+ "description": "stream_ref(xs, n) → {value}
\n Returns the element\nof stream xs
at position n
, \nwhere the first element has index 0.\nIterative process;\ntime: O(n)
, space: O(1)
,\nwhere n
is the length of xs
.\nLazy? Sort-of: stream_ref
only forces the computation of\n the first n
elements, and leaves the rest of\n the stream untouched.\n
\n
",
+ "meta": "func"
+ },
+ "stream_remove": {
+ "title": "stream_remove(v, xs) \u2192 {stream}",
+ "description": "stream_remove(v, xs) → {stream}
\n Returns a stream that results from\nxs
by removing the first item from xs
that\nis identical (===
) to v
.\nReturns the original\nstream if there is no occurrence. \nLazy? Yes: the result stream forces the construction of each next element\n
\n
",
+ "meta": "func"
+ },
+ "stream_remove_all": {
+ "title": "stream_remove_all(v, xs) \u2192 {stream}",
+ "description": "stream_remove_all(v, xs) → {stream}
\n Returns a stream that results from\nxs
by removing all items from xs
that\nare identical (===
) to v
.\nReturns the original\nstream if there is no occurrence. \nRecursive process.\nLazy? Yes: the result stream forces the construction of each next \nelement\n
\n
",
+ "meta": "func"
+ },
+ "stream_reverse": {
+ "title": "stream_reverse(xs) \u2192 {stream}",
+ "description": "stream_reverse(xs) → {stream}
\n Returns stream xs
in reverse\norder. Iterative process; time: O(n)
,\nspace: O(n)
, where n
is the length of xs
.\nThe process is iterative, but consumes space O(n)
\nbecause of the result stream.\nLazy? No: stream_reverse
\nforces the exploration of the entire stream\n
\n
",
+ "meta": "func"
+ },
+ "stream_tail": {
+ "title": "stream_tail(xs) \u2192 {Stream}",
+ "description": "stream_tail(xs) → {Stream}
\n assumes that the tail (second component) of the\npair {x} is a nullary function, and returns the result of\napplying that function. Throws an exception if the argument \nis not a pair, or if the tail is not a function.\nLaziness: Yes: {stream_tail} only forces the direct tail \nstream, but not the rest of the stream, i.e. not the tail \nof the tail, etc.\n
\n
",
+ "meta": "func"
+ },
+ "stream_to_list": {
+ "title": "stream_to_list(xs) \u2192 {list}",
+ "description": "stream_to_list(xs) → {list}
\n Given stream xs
, returns a list of same length with\nthe same elements as xs
in the same order.\nLaziness: No: stream_to_list
needs to force the whole \nstream.\n
\n
",
+ "meta": "func"
+ },
+ "stringify": {
+ "title": "stringify(v) \u2192 {string}",
+ "description": "stringify(v) → {string}
\n returns a string that represents the value
v
, using a\nnotation that is is consistent with \n
JSON, \nbut also displays
undefined
and function objects.\nSee also
textbook example.\n
\n
",
+ "meta": "func"
+ },
+ "tail": {
+ "title": "tail(p) \u2192 {value}",
+ "description": "tail(p) → {value}
\n returns tail (second component of given pair p
\n
\n
",
+ "meta": "func"
+ }
+}
\ No newline at end of file
diff --git a/src/editors/ace/theme/source.ts b/src/editors/ace/theme/source.ts
index 342d64ead..90f08ef36 100644
--- a/src/editors/ace/theme/source.ts
+++ b/src/editors/ace/theme/source.ts
@@ -125,6 +125,41 @@ function theme(acequire, exports, module) {
iVBORw0KGgoAAAANSUhEUgAAAAEAAAACCAYAAACZgbY\
nAAAAEklEQVQImWNgYGBgYHCLSvkPAAP3AgSDTRd4AAAAAElFTkSuQmCC) right repeat-y\
}\
+ .ace_dark.ace-source.ace_editor.ace_autocomplete {\
+ background-color: #2c3e50;\
+ border-color: #555555;\
+ color: white;\
+ }\
+ .ace_dark.ace-source.ace_editor.ace_autocomplete .ace_completion-highlight {\
+ color: #FF9D00;\
+ }\
+ .ace_dark.ace-source.ace_editor.ace_autocomplete .ace_content .ace_marker-layer .ace_active-line {\
+ border-color: #555555;\
+ background-color: #495a6b;\
+ }\
+ .ace_dark.ace-source.ace_editor.ace_autocomplete .ace_content .ace_marker-layer .ace_line-hover {\
+ border-color: #555555;\
+ background-color: #6b839a;\
+ }\
+ .ace_dark.ace-source.ace_editor.ace_autocomplete .ace_content.ace_text-layer .ace_rightAlignedText {\
+ color: #ced9e0;\
+ }\
+ .ace_tooltip.ace_doc-tooltip {\
+ width: 400px;\
+ max-height: 40vh;\
+ white-space: normal;\
+ overflow: auto;\
+ background-color: #495a6b;\
+ color: white;\
+ border-color:#555555;\
+ }\
+ .ace_tooltip.ace_doc-tooltip h4 {\
+ color: white;\
+ margin: 0 0 1em;\
+ }\
+ .ace_tooltip.ace_doc-tooltip a {\
+ color: #48aff0;\
+ }\
'
const dom = acequire('../lib/dom')
diff --git a/src/index.ts b/src/index.ts
index 29e96959a..0132e8db1 100644
--- a/src/index.ts
+++ b/src/index.ts
@@ -34,6 +34,8 @@ import { locationDummyNode } from './utils/astCreator'
import { validateAndAnnotate } from './validator/validator'
import { compileWithPrelude } from './vm/svml-compiler'
import { runWithProgram } from './vm/svml-machine'
+export { SourceDocumentation } from './editors/ace/docTooltip'
+import { getProgramNames } from './name-extractor'
export interface IOptions {
scheduler: 'preemptive' | 'async'
@@ -217,6 +219,16 @@ export function getAllOccurrencesInScope(
return getAllOccurrencesInScopeHelper(declarationNode.loc, program, identifierNode.name)
}
+export async function getNames(code: string, line: number, col: number): Promise {
+ const program = parse(code, createContext(), true)
+
+ if (!program) {
+ return []
+ }
+
+ return getProgramNames(program, { line, column: col })
+}
+
export async function runInContext(
code: string,
context: Context,
diff --git a/src/name-extractor/__tests__/autocomplete.ts b/src/name-extractor/__tests__/autocomplete.ts
new file mode 100644
index 000000000..8638a4418
--- /dev/null
+++ b/src/name-extractor/__tests__/autocomplete.ts
@@ -0,0 +1,429 @@
+// import { parse } from '../../parser/parser'
+import { getNames } from '../../index'
+import { NameDeclaration } from '../index'
+
+test('Test empty program does not generate names', async () => {
+ const code: string = 'f'
+ const line = 1
+ const col = 1
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = []
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test simple extraction of constant and variable names', async () => {
+ const code: string = '\
+ const foo1 = 1;\n\
+ let foo2 = 2;\n\
+ f\
+ '
+ const line = 3
+ const col = 1
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo2', meta: 'let' },
+ { name: 'foo1', meta: 'const' }
+ ]
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test simple extraction of function names', async () => {
+ const code: string =
+ '\
+ function foo1() {\n\
+ return true;\n\
+ }\n\
+ function foo2() {\n\
+ return true;\n\
+ }\n\
+ f\
+ '
+ const line = 7
+ const col = 1
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo2', meta: 'func' },
+ { name: 'foo1', meta: 'func' }
+ ]
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that names in smaller scope are not extracted', async () => {
+ const code: string =
+ '\
+ function baz1() {\n\
+ let bar1 = 1;\n\
+ }\n\
+ function baz2() {\n\
+ let bar2 = 1;\n\
+ }\n\
+ f\
+ '
+ const line = 7
+ const col = 1
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'baz2', meta: 'func' },
+ { name: 'baz1', meta: 'func' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+ expect(extractedNames).not.toContain({ name: 'bar1', meta: 'let' })
+ expect(extractedNames).not.toContain({ name: 'bar2', meta: 'let' })
+})
+
+test('Test that names in larger scope are extracted', async () => {
+ const code: string =
+ '\
+ let bar1 = 1;\n\
+ function foo1() {\n\
+ let bar3 = 1;\n\
+ function foo2() {\n\
+ b\n\
+ }\n\
+ const bar2 = 1;\n\
+ function bar4() {\n\
+ const baz = 1;\n\
+ }\n\
+ }\n\
+ '
+ const line = 5
+ const col = 3
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo1', meta: 'func' },
+ { name: 'bar4', meta: 'func' },
+ { name: 'bar2', meta: 'const' },
+ { name: 'foo2', meta: 'func' },
+ { name: 'bar3', meta: 'let' },
+ { name: 'bar1', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+ expect(extractedNames).not.toContain({ name: 'baz', meta: 'const' })
+})
+
+test('Test nested global scope', async () => {
+ const code: string =
+ '\
+ let bar = 1;\n\
+ function foo1() {\n\
+ function foo2() {\n\
+ function foo3() {\n\
+ b\n\
+ }\n\
+ }\
+ '
+ const line = 5
+ const col = 2
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo1', meta: 'func' },
+ { name: 'foo2', meta: 'func' },
+ { name: 'foo3', meta: 'func' },
+ { name: 'bar', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+// Function declarations
+
+test('Test that local and global variables are available in function declaration', async () => {
+ const code: string =
+ '\
+ let bar1 = 1;\n\
+ function foo1(){\n\
+ let bar2 = 2;\n\
+ function foo2()\n\
+ }\
+ '
+ const line = 4
+ const col = 15
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo1', meta: 'func' },
+ { name: 'bar2', meta: 'let' },
+ { name: 'bar1', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test accessing parameter names inside function', async () => {
+ const code: string =
+ '\
+ function foo1(bar1, baz1) {\n\
+ b\n\
+ }\n\
+ function foo2(bar2) {\n\
+ b\n\
+ }\n\
+ '
+ const line = 2
+ const col = 3
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo2', meta: 'func' },
+ { name: 'foo1', meta: 'func' },
+ { name: 'bar1', meta: 'let' },
+ { name: 'baz1', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+ expect(extractedNames).not.toContain({ name: 'baz2', meta: 'const' })
+})
+
+// For-loops
+
+test('Test accessing local block in for-loop parameter', async () => {
+ const code: string = '\
+ let bar = 1;\n\
+ let baz = 2;\n\
+ for (b) {\
+ '
+ const line = 3
+ const col = 6
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'baz', meta: 'let' },
+ { name: 'bar', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test accessing for-loop parameter in for-loop body', async () => {
+ const code: string = '\
+ for (let foo=10;) {\n\
+ f\n\
+ }\
+ '
+ const line = 2
+ const col = 3
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [{ name: 'foo', meta: 'let' }]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that for-loop local variable cannot be accessed outside loop', async () => {
+ const code: string = '\
+ for (let x=1; x<10; x=x+1) {\n\
+ let foo = x;\n\
+ }\n\
+ f\
+ '
+ const line = 4
+ const col = 1
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = []
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+// While-loops
+
+test('Test accessing local block in while-loop parameter', async () => {
+ const code: string = '\
+ let bar = 1;\n\
+ let baz = 2;\n\
+ while (b) {\
+ '
+ const line = 3
+ const col = 6
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'baz', meta: 'let' },
+ { name: 'bar', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that while-loop local variable cannot be accessed outside loop', async () => {
+ const code: string = '\
+ while (let x=1; x<10; x=x+1) {\n\
+ let foo = x;\n\
+ }\n\
+ f\
+ '
+ const line = 4
+ const col = 1
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = []
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+// Conditionals
+
+test('Test accessing local block in if-else parameter', async () => {
+ const code: string = '\
+ let bar = 1;\n\
+ let baz = 2;\n\
+ if (b) {\
+ '
+ const line = 3
+ const col = 5
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'baz', meta: 'let' },
+ { name: 'bar', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that local variable in if-block cannot be accessed in else-block', async () => {
+ const code: string = '\
+ if (true) {\n\
+ let foo = x;\n\
+ } else {\n\
+ f\n\
+ }\
+ '
+ const line = 4
+ const col = 1
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = []
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that variable in if- and else- cannot be accessed outside either block', async () => {
+ const code: string =
+ '\
+ if (true) {\n\
+ let foo = 2;\n\
+ } else {\n\
+ let foo = 1;\n\
+ }\n\
+ f\
+ '
+ const line = 6
+ const col = 1
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = []
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that variable in if cannot be accessed outside if-statement', async () => {
+ const code: string =
+ '\
+ function foo(baz) {\n\
+ if (baz) {\n\
+ let bar = 1;\n\
+ }\n\
+ b\n\
+ }\
+ '
+ const line = 5
+ const col = 2
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo', meta: 'func' },
+ { name: 'baz', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+// Blocks
+
+test('Test that declaration in blocks cannot be accessed outside block', async () => {
+ const code: string = '\
+ {\n\
+ let foo = 1;\n\
+ }\n\
+ f\
+ '
+ const line = 4
+ const col = 1
+ const expectedNames: NameDeclaration[] = []
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that declaration outside blocks can be accessed inside block', async () => {
+ const code: string = '\
+ let bar = 1;\n\
+ {\n\
+ let baz = 1;\n\
+ b\n\
+ }\n\
+ '
+ const line = 4
+ const col = 2
+ const expectedNames: NameDeclaration[] = [
+ { name: 'baz', meta: 'let' },
+ { name: 'bar', meta: 'let' }
+ ]
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+// Anonymous functions
+
+test('Test that declaration outside of anonymous functions can be accessed inside', async () => {
+ const code: string =
+ '\
+ let foo = () => { \n\
+ let baz = 1;\n\
+ b\n\
+ }\n\
+ let bar = 3;\n\
+ '
+ const line = 4
+ const col = 1
+ const expectedNames: NameDeclaration[] = [
+ { name: 'bar', meta: 'let' },
+ { name: 'foo', meta: 'let' },
+ { name: 'baz', meta: 'let' }
+ ]
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that declaration inside anonymous functions can be accessed in body', async () => {
+ const code: string =
+ '\
+ let foo = (bar1, bar2) => { \n\
+ let baz = 1;\n\
+ b\n\
+ }\n\
+ '
+ const line = 3
+ const col = 2
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo', meta: 'let' },
+ { name: 'bar1', meta: 'let' },
+ { name: 'bar2', meta: 'let' },
+ { name: 'baz', meta: 'let' }
+ ]
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+test('Test that declaration inside anonymous functions cannot be accessed outside', async () => {
+ const code: string = '\
+ let foo = (bar1, bar2) => { \n\
+ let baz = 1;\n\
+ }\n\
+ b\n\
+ '
+ const line = 4
+ const col = 1
+ const expectedNames: NameDeclaration[] = [{ name: 'foo', meta: 'let' }]
+ const extractedNames = await getNames(code, line, col)
+ expect(extractedNames).toMatchObject(expectedNames)
+})
+
+// Return statements
+
+test('Test that local and global variables are available in return statements', async () => {
+ const code: string =
+ '\
+ let bar1 = 1;\n\
+ function foo1(){\n\
+ let bar2 = 2;\n\
+ return b\n\
+ }\
+ '
+ const line = 4
+ const col = 7
+ const extractedNames = await getNames(code, line, col)
+ const expectedNames: NameDeclaration[] = [
+ { name: 'foo1', meta: 'func' },
+ { name: 'bar2', meta: 'let' },
+ { name: 'bar1', meta: 'let' }
+ ]
+ expect(extractedNames).toMatchObject(expectedNames)
+})
diff --git a/src/name-extractor/index.ts b/src/name-extractor/index.ts
new file mode 100644
index 000000000..18c453c0a
--- /dev/null
+++ b/src/name-extractor/index.ts
@@ -0,0 +1,161 @@
+import * as es from 'estree'
+
+export interface NameDeclaration {
+ name: string
+ meta: string
+}
+
+const KIND_FUNCTION = 'func'
+const KIND_LET = 'let'
+
+function isDeclaration(node: es.Node): boolean {
+ return node.type === 'VariableDeclaration' || node.type === 'FunctionDeclaration'
+}
+
+function isFunction(node: es.Node): boolean {
+ return (
+ node.type === 'FunctionDeclaration' ||
+ node.type === 'FunctionExpression' ||
+ node.type === 'ArrowFunctionExpression'
+ )
+}
+
+function isDummyName(name: string): boolean {
+ return name === '✖'
+}
+
+export function getProgramNames(prog: es.Node, cursorLoc: es.Position) {
+ function before(first: es.Position, second: es.Position) {
+ return first.line < second.line || (first.line === second.line && first.column <= second.column)
+ }
+
+ function inNode(nodeLoc: es.SourceLocation | null | undefined) {
+ if (nodeLoc === null || nodeLoc === undefined) {
+ return false
+ }
+ return before(nodeLoc.start, cursorLoc) && before(cursorLoc, nodeLoc.end)
+ }
+
+ const queue: es.Node[] = [prog]
+ const nameQueue: es.Node[] = []
+
+ while (queue.length > 0) {
+ const node = queue.pop()!
+ if (isDeclaration(node)) {
+ nameQueue.push(node)
+ }
+
+ if (inNode(node.loc)) {
+ if (isFunction(node)) {
+ // This is the only time we want to process raw identifiers
+ nameQueue.push(...(node as any).params)
+ }
+
+ const body = getNodeChildren(node)
+ if (body) {
+ for (const child of body) {
+ queue.push(child)
+ }
+ }
+ }
+ }
+
+ const res: any = {}
+ nameQueue
+ .map(node => getNames(node, (n: es.Node) => !inNode(n.loc)))
+ .reduce((prev, cur) => prev.concat(cur), []) // no flatmap feelsbad
+ .forEach(decl => {
+ res[decl.name] = decl
+ }) // Deduplicate, ensure deeper declarations overwrite
+ return Object.values(res)
+}
+
+function getNodeChildren(node: es.Node): es.Node[] {
+ switch (node.type) {
+ case 'Program':
+ return node.body
+ case 'BlockStatement':
+ return node.body
+ case 'WhileStatement':
+ return [node.test, node.body]
+ case 'ForStatement':
+ return [node.init, node.test, node.update, node.body].filter(
+ n => n !== undefined && n !== null
+ ) as es.Node[]
+ case 'ExpressionStatement':
+ return [node.expression]
+ case 'IfStatement':
+ const children = [node.test, node.consequent]
+ if (node.alternate !== undefined && node.alternate !== null) {
+ children.push(node.alternate)
+ }
+ return children
+ case 'ReturnStatement':
+ return node.argument ? [node.argument] : []
+ case 'FunctionDeclaration':
+ return [node.body]
+ case 'VariableDeclaration':
+ return node.declarations
+ .map(getNodeChildren)
+ .reduce((prev: es.Node[], cur: es.Node[]) => prev.concat(cur))
+ case 'VariableDeclarator':
+ return node.init ? [node.init] : []
+ case 'ArrowFunctionExpression':
+ return [node.body]
+ case 'FunctionExpression':
+ return [node.body]
+ case 'UnaryExpression':
+ return [node.argument]
+ case 'BinaryExpression':
+ return [node.left, node.right]
+ case 'LogicalExpression':
+ return [node.left, node.right]
+ case 'ConditionalExpression':
+ return [node.test, node.alternate, node.consequent]
+ case 'CallExpression':
+ return [...node.arguments, node.callee]
+ // case 'Identifier':
+ // case 'DebuggerStatement':
+ // case 'BreakStatement':
+ // case 'ContinueStatement':
+ // case 'MemberPattern':
+ case 'ArrayExpression':
+ return [...node.elements]
+ case 'AssignmentExpression':
+ return [node.left, node.right]
+ case 'MemberExpression':
+ return [node.object, node.property]
+ case 'Property':
+ return [node.key, node.value]
+ case 'ObjectExpression':
+ return [...node.properties]
+ case 'NewExpression':
+ return [...node.arguments, node.callee]
+ default:
+ return []
+ }
+}
+
+function getNames(node: es.Node, test: (node: es.Node) => boolean): NameDeclaration[] {
+ switch (node.type) {
+ case 'VariableDeclaration':
+ const delcarations: NameDeclaration[] = []
+ for (const decl of node.declarations) {
+ const id = decl.id
+ const name = (id as es.Identifier).name
+ if (!test(id) || !name || isDummyName(name)) {
+ continue
+ }
+ delcarations.push({ name, meta: node.kind })
+ }
+ return delcarations
+ case 'FunctionDeclaration':
+ return node.id && test(node.id) && !isDummyName(node.id.name)
+ ? [{ name: node.id.name, meta: KIND_FUNCTION }]
+ : []
+ case 'Identifier':
+ return test(node) && !isDummyName(node.name) ? [{ name: node.name, meta: KIND_LET }] : []
+ default:
+ return []
+ }
+}
diff --git a/src/transpiler/transpiler.ts b/src/transpiler/transpiler.ts
index f415bce31..d0a1c490a 100644
--- a/src/transpiler/transpiler.ts
+++ b/src/transpiler/transpiler.ts
@@ -4,8 +4,8 @@ import * as es from 'estree'
import { RawSourceMap, SourceMapGenerator } from 'source-map'
import { GLOBAL, GLOBAL_KEY_TO_ACCESS_NATIVE_STORAGE } from '../constants'
import { AllowedDeclarations, EvaluationMethod, Value } from '../types'
-import * as create from '../utils/astCreator'
import { ConstAssignment, UndefinedVariable } from '../errors/errors'
+import * as create from '../utils/astCreator'
/**
* This whole transpiler includes many many many many hacks to get stuff working.
diff --git a/src/typings/escodegen.d.ts b/src/typings/escodegen.d.ts
new file mode 100644
index 000000000..063399664
--- /dev/null
+++ b/src/typings/escodegen.d.ts
@@ -0,0 +1 @@
+declare module 'escodegen'
diff --git a/src/validator/__tests__/validator.ts b/src/validator/__tests__/validator.ts
index 392dd4a0c..001e70b0b 100644
--- a/src/validator/__tests__/validator.ts
+++ b/src/validator/__tests__/validator.ts
@@ -1,12 +1,12 @@
-import { stripIndent } from '../../utils/formatters'
-import { expectParsedError } from '../../utils/testing'
+import { simple } from 'acorn-walk/dist/walk'
+import * as es from 'estree'
import { mockContext } from '../../mocks/context'
import { parse } from '../../parser/parser'
-import { validateAndAnnotate } from '../validator'
-import * as es from 'estree'
-import { simple } from 'acorn-walk/dist/walk'
-import { getVariableDecarationName } from '../../utils/astCreator'
import { TypeAnnotatedNode } from '../../types'
+import { getVariableDecarationName } from '../../utils/astCreator'
+import { stripIndent } from '../../utils/formatters'
+import { expectParsedError } from '../../utils/testing'
+import { validateAndAnnotate } from '../validator'
export async function toValidatedAst(code: string) {
const context = mockContext(1)
diff --git a/tsconfig.json b/tsconfig.json
index b90954ed7..35246805f 100644
--- a/tsconfig.json
+++ b/tsconfig.json
@@ -23,6 +23,7 @@
"noImplicitAny": true,
"strictNullChecks": true,
"suppressImplicitAnyIndexErrors": true,
+ "resolveJsonModule": true,
"noUnusedLocals": true,
"incremental": true
},
diff --git a/yarn.lock b/yarn.lock
index 61e3804e1..97ddb06e8 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -146,6 +146,16 @@ acorn@^7.0.0:
resolved "https://registry.yarnpkg.com/acorn/-/acorn-7.1.1.tgz#e35668de0b402f359de515c5482a1ab9f89a69bf"
integrity sha512-add7dgA5ppRPxCFJoAGfMDi7PIBXq1RtGo7BhbLaxwrXPOmw8gq48Y9ozT01hUKy9byMjlR20EJhu5zlkErEkg==
+acorn@^7.0.0:
+ version "7.1.0"
+ resolved "https://registry.yarnpkg.com/acorn/-/acorn-7.1.0.tgz#949d36f2c292535da602283586c2477c57eb2d6c"
+ integrity sha512-kL5CuoXA/dgxlBbVrflsflzQ3PAas7RYZB52NOm/6839iVYJgKMJ3cQJD+t2i5+qFa8h3MDpEOJiS64E8JLnSQ==
+
+acorn@^7.0.0:
+ version "7.1.0"
+ resolved "https://registry.yarnpkg.com/acorn/-/acorn-7.1.0.tgz#949d36f2c292535da602283586c2477c57eb2d6c"
+ integrity sha512-kL5CuoXA/dgxlBbVrflsflzQ3PAas7RYZB52NOm/6839iVYJgKMJ3cQJD+t2i5+qFa8h3MDpEOJiS64E8JLnSQ==
+
ajv@^6.5.5:
version "6.10.0"
resolved "https://registry.yarnpkg.com/ajv/-/ajv-6.10.0.tgz#90d0d54439da587cd7e843bfb7045f50bd22bdf1"
@@ -950,6 +960,18 @@ escape-string-regexp@^1.0.2, escape-string-regexp@^1.0.5, escape-string-regexp@~
version "1.0.5"
resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4"
+escodegen@^1.14.1:
+ version "1.14.1"
+ resolved "https://registry.yarnpkg.com/escodegen/-/escodegen-1.14.1.tgz#ba01d0c8278b5e95a9a45350142026659027a457"
+ integrity sha512-Bmt7NcRySdIfNPfU2ZoXDrrXsG9ZjvDxcAlMfDUgRBjLOWTuIACXPBFJH7Z+cLb40JeQco5toikyc9t9P8E9SQ==
+ dependencies:
+ esprima "^4.0.1"
+ estraverse "^4.2.0"
+ esutils "^2.0.2"
+ optionator "^0.8.1"
+ optionalDependencies:
+ source-map "~0.6.1"
+
escodegen@^1.9.0:
version "1.10.0"
resolved "https://registry.yarnpkg.com/escodegen/-/escodegen-1.10.0.tgz#f647395de22519fbd0d928ffcf1d17e0dec2603e"
@@ -969,6 +991,11 @@ esprima@^4.0.0:
version "4.0.0"
resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.0.tgz#4499eddcd1110e0b218bacf2fa7f7f59f55ca804"
+esprima@^4.0.1:
+ version "4.0.1"
+ resolved "https://registry.yarnpkg.com/esprima/-/esprima-4.0.1.tgz#13b04cdb3e6c5d19df91ab6987a8695619b0aa71"
+ integrity sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==
+
estraverse@^4.2.0:
version "4.2.0"
resolved "https://registry.yarnpkg.com/estraverse/-/estraverse-4.2.0.tgz#0dee3fed31fcd469618ce7342099fc1afa0bdb13"