diff --git a/class/.explanatory.ini.swp b/class/.explanatory.ini.swp new file mode 100644 index 00000000..7cc575cb Binary files /dev/null and b/class/.explanatory.ini.swp differ diff --git a/class/.gitignore b/class/.gitignore new file mode 100644 index 00000000..bf5fbf37 --- /dev/null +++ b/class/.gitignore @@ -0,0 +1,16 @@ +output/ +*~ +build/ +class +*.prof +*.ini +libclass.a +*out +python/classy.c +*.pyc +python/build/ +*.dSYM +RealSpaceInterface/cache/ +.DS_Store +doc/manual/html +doc/manual/latex diff --git a/class/CPU b/class/CPU new file mode 100755 index 00000000..d12c8e54 --- /dev/null +++ b/class/CPU @@ -0,0 +1,427 @@ +################################################################### +# +# CPU, a CLASS Plotting Utility +# v1.3 +# Benjamin Audren, 07.11.2011 +# +# This is a small python program aimed to gain time when comparing two +# spectra, i.e. from CAMB and CLASS, or a non-linear spectrum to a +# linear one. It is designed to be used in a command line fashion, not +# being restricted to your CLASS directory, though it recognized mainly +# CLASS output format. Far from perfect, or complete, it could use any +# suggestion for enhancing it, just to avoid losing time on useless +# matters for others. Be warned that, when comparing with other +# format, the following is assumed: there are no empty line (especially +# at the end of file). Gnuplot comment lines (starting with a # are +# allowed). This issue will cause a non-very descriptive error in CPU, +# any suggestion for testing it is welcome. Example of use: To +# superimpose two different spectra and see their global shape : python +# CPU output/lcdm_z2_pk.dat output/lncdm_z2_pk.dat To precisely compare +# the non-linear contribution of one-loop w.r.t. to TRG method: python +# CPU -i output/lcdm_1l_z1_pk.dat output/lcdm_1l_z1_pk_nl_density.dat +# output/lcdm_trg_pk_nl_density.dat The documentation available with +# --help should cover any question. +################################################################### + +from scipy import * +from scipy import interpolate +import numpy as np +import os,sys,string,io,subprocess +import argparse + +# parser for input arguments + +parser = argparse.ArgumentParser(description='CPU, a CLASS Plotting Utility, specify wether you want to superimpose, divide or interpolate different files, and behold!', + epilog='''A standard usage would be, for instance : + python CPU output/test_1l_pk.dat output/test_1l_pk_nl_density.dat -i 0 + python CPU output/wmap_cl.dat output/planck_cl.dat''', +formatter_class=argparse.RawDescriptionHelpFormatter) +parser.add_argument('files', metavar='Files', + type=str, nargs='*', + help='the relative path of the desired file to plot\nfrom the root directory of CLASS') +parser.add_argument('-d, --divide', + dest='merging',action='store_const',const='blend_against',default='blend_together', + help='divide the spectra from different files. The k-values must be strictly identical (default: plot every graph on the same plot)') +parser.add_argument('-i, --interpolate',metavar='index', + nargs='?',dest='interp',const=True,default=False, + help='interpolate the spectra on each set of k-values if different. Use to compare two (or more) graphs with different k-values. If nothing more is specified, it will plot both index in gnuplot. Otherwise, just add -i 0 to plot only the first one.') +parser.add_argument('-t', metavar='pk, cl_lin,etc...', + help='specify the file type (whether pk or cl (if not specified, cl==cl_lin, other choices are cl_log and cl_ll for log linear), only needed if your file name does not already contain one of these keywords...') +parser.add_argument('-colnum',metavar='2, 3, ...', + help='specify the column you want to plot. By default, column is 2: you are plotting TT spectrum') +parser.add_argument('-x, --x11',metavar='gnuplot terminal', + dest='term',action='store_const',const='x11',default='aqua', + help='if your version of gnuplot does not support the aqua terminal, it will pick instead the x11 one, for crappier displays') +parser.add_argument('-p, --print', + dest='printfile',action='store_true',default=False, + help='print the graph directly in a .png file') +parser.add_argument('-r, --repeat', + dest='repeat',action='store_true',default=False, + help='repeat the step for all redshifts with same base name, whatever the desired action') +parser.add_argument('-c, --cleaning',metavar='path', + nargs='?',dest='cleaning',const=True,default=False, + help='remove all .plt files in the current directory (if none specified) : keep your folders clean !') + +# Remove all .plt, interp and divided files generated in output/ +# By default, will clean current directory. + +def clean(path): + pattern1,pattern2,pattern3='.plt','_interp.dat','_divided.dat' + path+="/" + print 'Cleaning {0} directory from .plt files ...'.format(path) + i=0 + for each in os.listdir(path): + if ( (each.rfind(pattern1)!=-1) or (each.rfind(pattern2)!=-1) or (each.rfind(pattern3)!=-1) ): + name= "{0}{1}".format(path,each) + print ' deleting {0}'.format(name) + if os.remove(name)!= None: + break + i+=1 + if i==0: + print ' ==> Already as clean as possible' + else: + print ' ==> Done' + +# Errors ########################### +def error_format(): + print " Hum... have you really provided a .dat file ?" + print " We apologise for the inconvenience, but CPU is exiting now" + exit() + +def error_type(): + print " Spectrum type unrecognized or unsupported yet, sorry!" + print " Please try the -t command in addition to your previous call" + print " We apologise for the inconvenience" + exit() + +def error_number_of_files(): + print " You specified a wrong number of files for the operation you demanded, maybe you do not want to divide only one file, for instance ?" + print " We apologise for the inconvenience" + exit() +#################################### + +# Subfunction called to write on the gnuplot script file the proper file names. + +def printstring(names): + print_file=names[0].rstrip(".dat") + print_file+=".ps" + print_string="set terminal po enhanced color\nset output '{0}'\nreplot".format(print_file) + print '{0} has been generated'.format(print_file) + return print_string + +# Subfunction called to write the most of the gnuplot script file according to options. + +def headers_plot_file(spectrum_type,names,plot_line,term): + tmp=open(names[0],"r") + + # printing option + if ((args.printfile is True) and (plot_line is not False)): + print_string=printstring(names) + else: + print_string="" + + # for interpolation: index choice option + if plot_line is True: + if args.interp is not True: + if args.interp is not False: + index_string=" index {0} ".format(args.interp) + else: + index_string=" " + else: + index_string=" " + + # if args colnum not specified, put it to 2, + if args.colnum is None: + args.colnum=2 + + + if spectrum_type=='cl_lin': + if plot_line is True: + plot_string="plot " + for name in names: + plot_string+="'{0}'".format(name)+"{0}u 1:{1} w l,".format(index_string,args.colnum) + plot_string=plot_string.rstrip(",") + plot_string+="\n" + else: + plot_string='' + return "set terminal {0} enhanced\n".format(term)+"set xlabel 'l'\nset ylabel 'l(l+1)C_l / 2{/Symbol p}'\nset xr [2:]\nset format y '%.0t*10^{%T}'\nset key right\nset title 'CLASS output'\n"+plot_string+print_string + elif spectrum_type=='cl_log': + for line in tmp: + if line.rfind('multipoles')!=-1: + lmax= line.split(None)[-1] + break + if plot_line is True: + plot_string="plot " + for name in names: + plot_string+="'{0}'".format(name)+"{0}u 1:{1} w l,".format(index_string,args.colnum) + plot_string=plot_string.rstrip(",") + plot_string+="\n" + else: + plot_string='' + return "set terminal {0} enhanced\n".format(term)+"set logscale x\nset xr [2:{0}]\n".format(lmax)+"set xlabel 'l'\nset format y '%.0t*10^{%T}'\n"+"set ylabel 'l(l+1)C_l / 2{/Symbol p}'\nset key left\nset title 'CLASS output'\n"+plot_string+print_string + elif spectrum_type=='cl_ll': + for line in tmp: + if line.rfind('multipoles')!=-1: + lmax= line.split()[-1] + break + if plot_line is True: + plot_string="plot " + for name in names: + plot_string+="'{0}'".format(name)+"{0}u (sqrt($1)):{1} w l,".format(index_string,args.colnum) + plot_string=plot_string.rstrip(",") + plot_string=plot_string+"\n" + else: + plot_string='' + return "set terminal {0} enhanced\n".format(term)+"set xlabel 'l'\nset ylabel 'l(l+1)C_l / 2{/Symbol p}'\nset key right\nset title 'CLASS output'\nset xtics ('2' (2),'100' (100), '500' (500), '1000' (1000), '1500' (1500), '2000' (2000),'2500' (2500))"+"\nset format y '%.0t*10^{%T}'\n"+"set xr [2:{0}]\n".format(lmax)+plot_string+print_string + elif spectrum_type=='pk': + if plot_line is True: + plot_string="plot " + for name in names: + plot_string+="'{0}'".format(name)+"{0}w l,".format(index_string) + plot_string=plot_string.rstrip(",") + plot_string+="\n" + else: + plot_string="" + for line in tmp: + if line.rfind('redshift')!=-1: + z= line.split("=")[1] + z= z.rstrip("\n") + break + else: + z= 'I have no idea' + return "set terminal {0} enhanced\n".format(term)+"set logscale\nset xlabel 'k (h/Mpc)'\nset ylabel 'P_k (Mpc/h)^3'\nset key right\nset title 'Power spectrum at z={0}'\n".format(z)+plot_string+print_string + else: + return None + tmp.close() + +# Print all asked files one next to the other (default operation if files with different k values) +def blend_together(names,spectrum_type,term): + gnuplot_file=names[0].replace(".dat",".plt") + if gnuplot_file==names[0]: + error_format() + print ' creating {0}'.format(gnuplot_file) + plotfile = open(gnuplot_file, "w") + plotfile.write(headers_plot_file(spectrum_type, names,True,term)) + plotfile.close() + _plot(gnuplot_file) + +# Print all asked files with respect to the same k (or anything) values, all y-data being divided by the y data of the first file. +# Only valid if the k values are exactly the same (values and number of values). +def blend_against(names,spectrum_type,term): + gnuplot_file=names[0].replace(".dat",".plt") + data_file=names[0].replace(".dat","_divided.dat") + if gnuplot_file==names[0]: + error_format() + print ' creating {0} and {1}'.format(gnuplot_file,data_file) + string=['' for rows in range(10000)] + imax=0 + datafile=open(data_file,"w") + for name in names: + i=0 + tmp=open(name,"r") + for line in tmp: + if ((line.find('#')==-1) and (line.rfind('000000')==-1)): + string[i]=string[i]+line.rstrip("\n")+"\t" + if i>imax: + imax=i + i+=1 + tmp.close() + for i in range(imax): + datafile.write(string[i]+"\n") + plotfile = open(gnuplot_file,"w") + plotfile.write(headers_plot_file(spectrum_type,names,False,term)) + plot_string='unset logscale\nplot ' + x_base=1 + field_base=2 + field=2 + size=len(names) + for i in range(size): + field+=2 + plot_string+="'{0}' u {1}:(${2}/${3}) w l,".format(data_file,x_base,field,field_base) + plot_string=plot_string.rstrip(',') + plot_string+="\n" + plotfile.write(plot_string) + plotfile.close() + datafile.close() + _plot(gnuplot_file) + +# If k values are different, an interpolation is done and outputs a data file. For a two files case: +# File 1 contains ( k1 | P1(k1) ), File 2 ( k2 | P2(k2) ). The data file created will contain: +# k1 | P1(k1) | P2(k1)_interp +#(blank space for gnuplot using index 0, etc) +# k2 | P1(k2)_interp | P2(k2) +def blend_against_interp(names,spectrum_type,term): + gnuplot_file=names[0].replace(".dat",".plt") + data_file=names[0].replace(".dat","_interp.dat") + if gnuplot_file==names[0]: + error_format() + print ' creating {0} and {1}'.format(gnuplot_file,data_file) + plotfile = open(gnuplot_file,"w") + l=0 + jmax=[0 for col in range(10)] + lmax=0 + kmax=10000000 + kmin=0 + spam = np.array([[[0 for col in range(10)] for row in range(10000)] for depth in range(2)],dtype=float) + for name in names: + currentfile = open(name,"r") + print ' reading {0}..'.format(name) + j=0 + for line in currentfile: + if (line.find('#')==-1): + line=line.split() + spam[0,j,l]=float(line[0]) + spam[1,j,l]=float(line[1]) + j+=1 + jmax[l]=j + if spam[0,jmax[l]-1,l]<=kmax: + kmax=spam[0,jmax[l]-1,l] + if spam[0,0,l]>=kmin: + kmin=spam[0,0,l] + l+=1 + currentfile.close() + lmax=l + lower_bound=[0 for col in range(10)] + upper_bound=[0 for col in range(10)] + #determining the upper and lower bound for each file, to only do interpolation + for l in range (lmax): + for j in range (jmax[l]): + if ((spam[0,j,l]=kmin)): + lower_bound[l]=j+1 + if (spam[0,j,l]<=kmax): + upper_bound[l]=j + print ' -> done' + + #creating the new data file + curves=[np.array for row in range(lmax)] + interpolated=[np.array for row in range(lmax)] + for l in range (lmax): + x=spam[0,lower_bound[l]:upper_bound[l],l] + y=spam[1,lower_bound[l]:upper_bound[l],l] + curves[l]=interpolate.splrep(x,y) + + datafile = open(data_file,"w") + for l in range (lmax): + for ll in range(lmax): + if ll==l: + interpolated[ll]=spam[1,lower_bound[l]:upper_bound[l],l] + else: + x2=spam[0,lower_bound[l]:upper_bound[l],l] + interpolated[ll]=interpolate.splev(x2,curves[ll],der=0) + for j in range(upper_bound[l]-lower_bound[l]-2): + data_string='' + for ll in range(lmax): + data_string=data_string+str((interpolated[ll])[j+1])+"\t" + datafile.write(str(spam[0,j+lower_bound[l]+1,l])+"\t"+data_string+"\n") + datafile.write("\n\n") + datafile.close() + + # if index chosen + if args.interp is not True: + index_string_interp=" index {0}".format(args.interp) + else: + index_string_interp="" + plotfile = open(gnuplot_file,"w") + plotfile.write(headers_plot_file(spectrum_type,names,False,term)) + plotfile.write("unset logscale \n") + if args.t in ['cl_log', 'pk']: + plotfile.write("set logscale x\n") + plotfile.write("set xr [{0}:{1}]\n".format(kmin,kmax)) + #plotfile.write("set yr [-0.001:0.005]\n") + plot_string="plot " + for l in range(lmax-1): + plot_string+="'{0}' {1} u 1:(${2}/$2-1) w l,".format(data_file,index_string_interp,l+3) + plot_string=plot_string.rstrip(",") + plot_string=plot_string+"\n" + plotfile.write(plot_string) + + if (args.printfile is True): + plotfile.write(printstring(names)) + + plotfile.close() + _plot(gnuplot_file) + +# Launch session of gnuplot with generated gnuplot script file +def _plot(gnuplot_file): + os.system("gnuplot -persist '{0}'".format(gnuplot_file)) + + +####################################################### +################## MAIN PART ########################## +####################################################### + +print '~~~ CPU, a CLASS Plotting Utility ~~~' +args = parser.parse_args() + +# check if the user want to clean its directory first +if args.cleaning is not False: + if args.cleaning is not True: + clean(args.cleaning) + else: + clean(os.getcwd()) + exit() + +# if there are no argument in the input, print usage +if len(args.files)==0: + parser.print_usage() + exit() + +# if the first file name contains cl or pk, infer the type of desired spectrum +if ((args.files[0].rfind('cl')!=-1) and (args.t is None)): + spectrum_type='cl_lin' + args.t = 'cl_lin' +elif args.files[0].rfind('pk')!=-1: + spectrum_type='pk' + args.t = 'pk' +elif args.t is not None: + spectrum_type=args.t +else: + error_type() + +# repeater +temp_path=args.files[0].split("/") +if len(temp_path)> 1: + path=temp_path[-2] +else: + path=os.getcwd() +list_file=['' for i in range(len(args.files)*10)] +if (temp_path[-1].rfind("z")!=-1 and args.repeat is True): + root_name=temp_path[-1].split("z")[-2] + for any in range (0,len(args.files)): + extension_name=args.files[any].split("/")[-1].split("_")[-1] + i=0 + for each in os.listdir(path): + if (("z" in each) and (each.split("z")[-2]==root_name) and (each.split("_")[-1]==extension_name)): + if len(temp_path)>1: + list_file[any+len(args.files)*i]=temp_path[-2]+"/"+each + else: + list_file[any+len(args.files)*i]=each + i+=1 + if args.repeat is True: + repeat_len=i-1 + else: + repeat_len=0 +else: + for any in range(0,len(args.files)): + list_file[any]=args.files[any] + repeat_len=0 + + +# actual computation +for i in range(0,repeat_len+1): + local_files=['' for k in range(len(args.files))] + for j in range(0,len(args.files)): + local_files[j]=list_file[j+len(args.files)*i] + if args.interp is False: + if args.merging=='blend_together': + blend_together(local_files,spectrum_type,args.term) + else: + if len(local_files)<2: + error_number_of_files() + else: + blend_against(local_files,spectrum_type,args.term) + else: + print '**interpolating (please wait)' + blend_against_interp(local_files,spectrum_type,args.term) + +exit() diff --git a/class/CPU.py b/class/CPU.py new file mode 100755 index 00000000..df6afed0 --- /dev/null +++ b/class/CPU.py @@ -0,0 +1,622 @@ +#!/usr/bin/env python +""" +.. module:: CPU + :synopsis: CPU, a CLASS Plotting Utility +.. moduleauthor:: Benjamin Audren +.. credits:: Benjamin Audren, Jesus Torrado +.. version:: 2.0 + +This is a small python program aimed to gain time when comparing two spectra, +e.g. from CAMB and CLASS, or a non-linear spectrum to a linear one. + +It is designed to be used in a command line fashion, not being restricted to +your CLASS directory, though it recognizes mainly CLASS output format. Far from +perfect, or complete, it could use any suggestion for enhancing it, +just to avoid losing time on useless matters for others. + +Be warned that, when comparing with other format, the following is assumed: +there are no empty line (especially at the end of file). Gnuplot comment lines +(starting with a # are allowed). This issue will cause a non-very descriptive +error in CPU, any suggestion for testing it is welcome. + +Example of use: +- To superimpose two different spectra and see their global shape : +python CPU.py output/lcdm_z2_pk.dat output/lncdm_z2_pk.dat +- To see in details their ratio: +python CPU.py output/lcdm_z2_pk.dat output/lncdm_z2_pk.dat -r + +The "PlanckScale" is taken with permission from Jesus Torrado's: +cosmo_mini_toolbox, available under GPLv3 at +https://github.com/JesusTorrado/cosmo_mini_toolbox + +""" + +from __future__ import unicode_literals, print_function + +# System imports +import os +import sys +import argparse + +# Numerics +import numpy as np +from numpy import ma +from scipy.interpolate import InterpolatedUnivariateSpline +from math import floor + +# Plotting +import matplotlib.pyplot as plt +from matplotlib import scale as mscale +from matplotlib.transforms import Transform +from matplotlib.ticker import FixedLocator + + +def CPU_parser(): + parser = argparse.ArgumentParser( + description=( + 'CPU, a CLASS Plotting Utility, specify wether you want\n' + 'to superimpose, or plot the ratio of different files.'), + epilog=( + 'A standard usage would be, for instance:\n' + 'python CPU.py output/test_pk.dat output/test_pk_nl_density.dat' + ' -r\npython CPU.py output/wmap_cl.dat output/planck_cl.dat'), + formatter_class=argparse.RawDescriptionHelpFormatter) + + parser.add_argument( + 'files', type=str, nargs='*', help='Files to plot') + parser.add_argument('-r', '--ratio', dest='ratio', action='store_true', + help='Plot the ratio of the spectra') + parser.add_argument('-y', '--y-axis', dest='y_axis', nargs='+', + help='specify the fields you want to plot.') + parser.add_argument('-x', '--x-axis', dest='x_axis', type=str, + help='specify the field to be used on the x-axis') + parser.add_argument('--scale', type=str, + choices=['lin', 'loglog', 'loglin', 'george'], + help='Specify the scale to use for the plot') + parser.add_argument('--xlim', dest='xlim', nargs='+', type=float, + default=[], help='Specify the x range') + parser.add_argument('--ylim', dest='ylim', nargs='+', type=float, + default=[], help='Specify the y range') + parser.add_argument( + '-p, --print', + dest='printfile', default='', + help=('print the graph directly in a file. If no name is specified, it' + 'uses the name of the first input file')) + parser.add_argument( + '--repeat', + dest='repeat', action='store_true', default=False, + help='repeat the step for all redshifts with same base name') + return parser + + +def plot_CLASS_output(files, x_axis, y_axis, ratio=False, printing='', + output_name='', extension='', x_variable='', + scale='lin', xlim=[], ylim=[]): + """ + Load the data to numpy arrays, write all the commands for plotting to a + Python script for further refinment, and display them. + + Inspired heavily by the matlab version by Thomas Tram + + Parameters + ---------- + files : list + List of files to plot + x-axis : string + name of the column to use as the x coordinate + y-axis : list, str + List of items to plot, which should match the way they appear in the + file, for instance: ['TT', 'BB] + + Keyword Arguments + ----------------- + ratio : bool + If set to yes, plots the ratio of the files, taking as a reference the + first one + output_name : str + Specify a different name for the produced figure (by default, it takes + the name of the first file, and replace the .dat by .pdf) + extension : str + + """ + # Define the python script name, and the pdf path + python_script_path = os.path.splitext(files[0])[0]+'.py' + + # The variable text will contain all the lines to be printed in the end to + # the python script path, joined with newline characters. Beware of the + # indentation. + text = ['import matplotlib.pyplot as plt', + 'import numpy as np', + 'import itertools', ''] + + # Load all the graphs + data = [] + for data_file in files: + data.append(np.loadtxt(data_file)) + + # Create the full_path_files list, that contains the absolute path, so that + # the future python script can import them directly. + full_path_files = [os.path.abspath(elem) for elem in files] + + text += ['files = %s' % full_path_files] + text += ['data = []', + 'for data_file in files:', + ' data.append(np.loadtxt(data_file))'] + + # Recover the base name of the files, everything before the dot + roots = [elem.split(os.path.sep)[-1].split('.')[0] for elem in files] + text += ['roots = [%s]' % ', '.join(["'%s'" % root for root in roots])] + + # Create the figure and ax objects + fig, ax = plt.subplots() + text += ['', 'fig, ax = plt.subplots()'] + + # if ratio is not set, then simply plot them all + original_y_axis = y_axis + legend = [] + if not ratio: + for index, curve in enumerate(data): + # Recover the number of columns in the first file, as well as their + # title. + num_columns, names, tex_names = extract_headers(files[index]) + + text += ['', 'index, curve = %i, data[%i]' % (index, index)] + # Check if everything is in order + if num_columns == 2: + y_axis = [names[1]] + elif num_columns > 2: + # in case y_axis was only a string, cast it to a list + if isinstance(original_y_axis, str): + y_axis = [original_y_axis] + else: + y_axis = original_y_axis + + # Store the selected text and tex_names to the script + selected = [] + for elem in y_axis: + selected.extend( + [name for name in names if name.find(elem) != -1 and + name not in selected]) + if not y_axis: + selected = names[1:] + y_axis = selected + + # Decide for the x_axis, by default the index will be set to zero + x_index = 0 + if x_axis: + for index_name, name in enumerate(names): + if name.find(x_axis) != -1: + x_index = index_name + break + # Store to text + text += ['y_axis = %s' % selected] + text += ['tex_names = %s' % [elem for (elem, name) in + zip(tex_names, names) if name in selected]] + text += ["x_axis = '%s'" % tex_names[x_index]] + text += ["ylim = %s" % ylim] + text += ["xlim = %s" % xlim] + + for selec in y_axis: + index_selec = names.index(selec) + plot_line = 'ax.' + if scale == 'lin': + plot_line += 'plot(curve[:, %i], curve[:, %i])' % ( + x_index, index_selec) + ax.plot(curve[:, x_index], curve[:, index_selec]) + elif scale == 'loglog': + plot_line += 'loglog(curve[:, %i], abs(curve[:, %i]))' % ( + x_index, index_selec) + ax.loglog(curve[:, x_index], abs(curve[:, index_selec])) + elif scale == 'loglin': + plot_line += 'semilogx(curve[:, %i], curve[:, %i])' % ( + x_index, index_selec) + ax.semilogx(curve[:, x_index], curve[:, index_selec]) + elif scale == 'george': + plot_line += 'plot(curve[:, %i], curve[:, %i])' % ( + x_index, index_selec) + ax.plot(curve[:, x_index], curve[:, index_selec]) + ax.set_xscale('planck') + text += [plot_line] + + legend.extend([roots[index]+': '+elem for elem in y_axis]) + + ax.legend(legend, loc='best') + text += ["", + "ax.legend([root+': '+elem for (root, elem) in", + " itertools.product(roots, y_axis)], loc='best')", + ""] + else: + ref = data[0] + num_columns, ref_curve_names, ref_tex_names = extract_headers(files[0]) + # Check if everything is in order + if num_columns == 2: + y_axis_ref = [ref_curve_names[1]] + elif num_columns > 2: + # in case y_axis was only a string, cast it to a list + if isinstance(original_y_axis, str): + y_axis_ref = [original_y_axis] + else: + y_axis_ref = original_y_axis + + # Store the selected text and tex_names to the script + selected = [] + for elem in y_axis_ref: + selected.extend([name for name in ref_curve_names if name.find(elem) != -1 and + name not in selected]) + y_axis_ref = selected + + # Decide for the x_axis, by default the index will be set to zero + x_index_ref = 0 + if x_axis: + for index_name, name in enumerate(ref_curve_names): + if name.find(x_axis) != -1: + x_index_ref = index_name + break + + for idx in range(1, len(data)): + current = data[idx] + num_columns, names, tex_names = extract_headers(files[idx]) + + # Check if everything is in order + if num_columns == 2: + y_axis = [names[1]] + elif num_columns > 2: + # in case y_axis was only a string, cast it to a list + if isinstance(original_y_axis, str): + y_axis = [original_y_axis] + else: + y_axis = original_y_axis + + # Store the selected text and tex_names to the script + selected = [] + for elem in y_axis: + selected.extend([name for name in names if name.find(elem) != -1 and + name not in selected]) + y_axis = selected + + text += ['y_axis = %s' % selected] + text += ['tex_names = %s' % [elem for (elem, name) in + zip(tex_names, names) if name in selected]] + + # Decide for the x_axis, by default the index will be set to zero + x_index = 0 + if x_axis: + for index_name, name in enumerate(names): + if name.find(x_axis) != -1: + x_index = index_name + break + + text += ["x_axis = '%s'" % tex_names[x_index]] + for selec in y_axis: + # Do the interpolation + axis = ref[:, x_index_ref] + reference = ref[:, ref_curve_names.index(selec)] + #plt.loglog(current[:, x_index], current[:, names.index(selec)]) + #plt.show() + #interpolated = splrep(current[:, x_index], + #current[:, names.index(selec)]) + interpolated = InterpolatedUnivariateSpline(current[:, x_index], + current[:, names.index(selec)]) + if scale == 'lin': + #ax.plot(axis, splev(ref[:, x_index_ref], + #interpolated)/reference-1) + ax.plot(axis, interpolated(ref[:, x_index_ref])/reference-1) + elif scale == 'loglin': + #ax.semilogx(axis, splev(ref[:, x_index_ref], + #interpolated)/reference-1) + ax.semilogx(axis, interpolated(ref[:, x_index_ref])/reference-1) + elif scale == 'loglog': + raise InputError( + "loglog plot is not available for ratios") + + if 'TT' in names: + ax.set_xlabel('$\ell$', fontsize=16) + text += ["ax.set_xlabel('$\ell$', fontsize=16)"] + elif 'P' in names: + ax.set_xlabel('$k$ [$h$/Mpc]', fontsize=16) + text += ["ax.set_xlabel('$k$ [$h$/Mpc]', fontsize=16)"] + else: + ax.set_xlabel(tex_names[x_index], fontsize=16) + text += ["ax.set_xlabel('%s', fontsize=16)" % tex_names[x_index]] + if xlim: + if len(xlim) > 1: + ax.set_xlim(xlim) + text += ["ax.set_xlim(xlim)"] + else: + ax.set_xlim(xlim[0]) + text += ["ax.set_xlim(xlim[0])"] + ax.set_ylim() + text += ["ax.set_ylim()"] + if ylim: + if len(ylim) > 1: + ax.set_ylim(ylim) + text += ["ax.set_ylim(ylim)"] + else: + ax.set_ylim(ylim[0]) + text += ["ax.set_ylim(ylim[0])"] + text += ['plt.show()'] + plt.show() + + # If the use wants to print the figure to a file + if printing: + fig.savefig(printing) + text += ["fig.savefig('%s')" % printing] + + # Write to the python file all the issued commands. You can then reproduce + # the plot by running "python output/something_cl.dat.py" + with open(python_script_path, 'w') as python_script: + print('Creating a python script to reproduce the figure') + print('--> stored in %s' % python_script_path) + python_script.write('\n'.join(text)) + + # If the use wants to print the figure to a file + if printing: + fig.savefig(printing) + + +class FormatError(Exception): + """Format not recognised""" + pass + + +class TypeError(Exception): + """Spectrum type not recognised""" + pass + + +class NumberOfFilesError(Exception): + """Invalid number of files""" + pass + + +class InputError(Exception): + """Incompatible input requirements""" + pass + + +def replace_scale(string): + """ + This assumes that the string starts with "(.)", which will be replaced by + (8piG/3) + + >>> print replace_scale('(.)toto') + >>> '(8\\pi G/3)toto' + """ + string_list = list(string) + string_list.pop(1) + string_list[1:1] = list('8\\pi G/3') + return ''.join(string_list) + + +def process_long_names(long_names): + """ + Given the names extracted from the header, return two arrays, one with the + short version, and one tex version + + >>> names, tex_names = process_long_names(['(.)toto', 'proper time [Gyr]']) + >>> print names + >>> ['toto', 'proper time'] + >>> print tex_names + >>> ['(8\\pi G/3)toto, 'proper time [Gyr]'] + + """ + names = [] + tex_names = [] + # First pass, to remove the leading scales + for name in long_names: + # This can happen in the background file + if name.startswith('(.)', 0): + temp_name = name[3:] + names.append(temp_name) + tex_names.append(replace_scale(name)) + # Otherwise, we simply + else: + names.append(name) + tex_names.append(name) + + # Finally, remove any extra spacing + names = [''.join(elem.split()) for elem in names] + return names, tex_names + + +def extract_headers(header_path): + with open(header_path, 'r') as header_file: + header = [line for line in header_file if line[0] == '#'] + header = header[-1] + + # Count the number of columns in the file, and recover their name. Thanks + # Thomas Tram for the trick + indices = [i+1 for i in range(len(header)) if + header.startswith(':', i)] + num_columns = len(indices) + long_names = [header[indices[i]:indices[(i+1)]-3].strip() if i < num_columns-1 + else header[indices[i]:].strip() + for i in range(num_columns)] + + # Process long_names further to handle special cases, and extract names, + # which will correspond to the tags specified in "y_axis". + names, tex_names = process_long_names(long_names) + + return num_columns, names, tex_names + + +def main(): + print('~~~ Running CPU, a CLASS Plotting Utility ~~~') + parser = CPU_parser() + # Parse the command line arguments + args = parser.parse_args() + + # if there are no argument in the input, print usage + if len(args.files) == 0: + parser.print_usage() + return + + # if the first file name contains cl or pk, infer the type of desired + # spectrum + if not args.y_axis: + if args.files[0].rfind('cl') != -1: + scale = 'loglog' + elif args.files[0].rfind('pk') != -1: + scale = 'loglog' + else: + scale = 'lin' + args.y_axis = [] + else: + scale = '' + if not args.scale: + if scale: + args.scale = scale + else: + args.scale = 'lin' + + # Remove extra spacing in the y_axis list + args.y_axis = [''.join(elem.split()) for elem in args.y_axis] + # If ratio is asked, but only one file was passed in argument, politely + # complain + if args.ratio: + if len(args.files) < 2: + raise NumberOfFilesError( + "If you want me to compute a ratio between two files, " + "I strongly encourage you to give me at least two of them.") + # actual plotting. By default, a simple superposition of the graph is + # performed. If asked to be divided, the ratio is shown - whether a need + # for interpolation arises or not. + if args.ratio and args.scale == 'loglog': + print("Defaulting to loglin scale") + args.scale = 'loglin' + + plot_CLASS_output(args.files, args.x_axis, args.y_axis, + ratio=args.ratio, printing=args.printfile, + scale=args.scale, xlim=args.xlim, ylim=args.ylim) + + +# Helper code from cosmo_mini_toolbox, by Jesus Torrado, available fully at +# https://github.com/JesusTorrado/cosmo_mini_toolbox, to use the log then +# linear scale for the multipole axis when plotting Cl. +nonpos = "mask" +change = 50.0 +factor = 500. + + +def _mask_nonpos(a): + """ + Return a Numpy masked array where all non-positive 1 are + masked. If there are no non-positive, the original array + is returned. + """ + mask = a <= 0.0 + if mask.any(): + return ma.MaskedArray(a, mask=mask) + return a + + +def _clip_smaller_than_one(a): + a[a <= 0.0] = 1e-300 + return a + + +class PlanckScale(mscale.ScaleBase): + """ + Scale used by the Planck collaboration to plot Temperature power spectra: + base-10 logarithmic up to l=50, and linear from there on. + + Care is taken so non-positive values are not plotted. + """ + name = 'planck' + + def __init__(self, axis, **kwargs): + pass + + def set_default_locators_and_formatters(self, axis): + axis.set_major_locator( + FixedLocator( + np.concatenate((np.array([2, 10, change]), + np.arange(500, 2500, 500))))) + axis.set_minor_locator( + FixedLocator( + np.concatenate((np.arange(2, 10), + np.arange(10, 50, 10), + np.arange(floor(change/100), 2500, 100))))) + + def get_transform(self): + """ + Return a :class:`~matplotlib.transforms.Transform` instance + appropriate for the given logarithm base. + """ + return self.PlanckTransform(nonpos) + + def limit_range_for_scale(self, vmin, vmax, minpos): + """ + Limit the domain to positive values. + """ + return (vmin <= 0.0 and minpos or vmin, + vmax <= 0.0 and minpos or vmax) + + class PlanckTransform(Transform): + input_dims = 1 + output_dims = 1 + is_separable = True + has_inverse = True + + def __init__(self, nonpos): + Transform.__init__(self) + if nonpos == 'mask': + self._handle_nonpos = _mask_nonpos + else: + self._handle_nonpos = _clip_nonpos + + def transform_non_affine(self, a): + lower = a[np.where(a<=change)] + greater = a[np.where(a> change)] + if lower.size: + lower = self._handle_nonpos(lower * 10.0)/10.0 + if isinstance(lower, ma.MaskedArray): + lower = ma.log10(lower) + else: + lower = np.log10(lower) + lower = factor*lower + if greater.size: + greater = (factor*np.log10(change) + (greater-change)) + # Only low + if not(greater.size): + return lower + # Only high + if not(lower.size): + return greater + return np.concatenate((lower, greater)) + + def inverted(self): + return PlanckScale.InvertedPlanckTransform() + + class InvertedPlanckTransform(Transform): + input_dims = 1 + output_dims = 1 + is_separable = True + has_inverse = True + + def transform_non_affine(self, a): + lower = a[np.where(a<=factor*np.log10(change))] + greater = a[np.where(a> factor*np.log10(change))] + if lower.size: + if isinstance(lower, ma.MaskedArray): + lower = ma.power(10.0, lower/float(factor)) + else: + lower = np.power(10.0, lower/float(factor)) + if greater.size: + greater = (greater + change - factor*np.log10(change)) + # Only low + if not(greater.size): + return lower + # Only high + if not(lower.size): + return greater + return np.concatenate((lower, greater)) + + def inverted(self): + return PlanckTransform() + +# Finished. Register the scale! +mscale.register_scale(PlanckScale) + +if __name__ == '__main__': + sys.exit(main()) diff --git a/class/Makefile b/class/Makefile old mode 100644 new mode 100755 index 6bddd5a0..52530996 --- a/class/Makefile +++ b/class/Makefile @@ -1,203 +1,207 @@ -#Some Makefile for CLASS. -#Julien Lesgourgues, 28.11.2011 - -MDIR := $(shell pwd) -WRKDIR = $(MDIR)/build - -.base: - if ! [ -e $(WRKDIR) ]; then mkdir $(WRKDIR) ; mkdir $(WRKDIR)/lib; fi; - touch build/.base - -vpath %.c source:tools:main:test -vpath %.o build -vpath .base build - -######################################################## -###### LINES TO ADAPT TO YOUR PLATEFORM ################ -######################################################## - -# your C compiler: -CC = gcc -#CC = icc -#CC = pgcc - -# your tool for creating static libraries: -AR = ar rv - -# (OPT) your python interpreter -PYTHON = python - -# your optimization flag -OPTFLAG = -O3 -ffast-math #-march=native -#OPTFLAG = -Ofast -ffast-math #-march=native -#OPTFLAG = -fast - -# your openmp flag (comment for compiling without openmp) -# OMPFLAG = -fopenmp -# OMPFLAG = -mp -mp=nonuma -mp=allcores -g -# OMPFLAG = -openmp - -# all other compilation flags -CCFLAG = -g -fPIC -LDFLAG = -g -fPIC - -# leave blank to compile without HyRec, or put path to HyRec directory -# (with no slash at the end: e.g. hyrec or ../hyrec) -#HYREC = hyrec - -######################################################## -###### IN PRINCIPLE THE REST SHOULD BE LEFT UNCHANGED ## -######################################################## - -# pass current working directory to the code -CCFLAG += -D__CLASSDIR__='"$(MDIR)"' - -# where to find include files *.h -INCLUDES = -I../include - -# automatically add external programs if needed. First, initialize to blank. -EXTERNAL = - -# Try to automatically avoid an error 'error: can't combine user with ...' -# which sometimes happens with brewed Python on OSX: -CFGFILE=$(shell $(PYTHON) -c "import sys; print(sys.prefix+'/lib/'+'python'+'.'.join(['%i' % e for e in sys.version_info[0:2]])+'/distutils/distutils.cfg')") -PYTHONPREFIX=$(shell grep -s "prefix" $(CFGFILE)) -ifeq ($(PYTHONPREFIX),) -PYTHONFLAGS=--user -else -PYTHONFLAGS= -endif - -# eventually update flags for including HyRec -ifneq ($(HYREC),) -vpath %.c $(HYREC) -CCFLAG += -DHYREC -#LDFLAGS += -DHYREC -INCLUDES += -I../hyrec -EXTERNAL += hyrectools.o helium.o hydrogen.o history.o -endif - -%.o: %.c .base - cd $(WRKDIR);$(CC) $(OPTFLAG) $(OMPFLAG) $(CCFLAG) $(INCLUDES) -c ../$< -o $*.o - -TOOLS = growTable.o dei_rkck.o sparse.o evolver_rkck.o evolver_ndf15.o arrays.o parser.o quadrature.o hyperspherical.o common.o - -SOURCE = input.o background.o thermodynamics.o perturbations.o primordial.o nonlinear.o transfer.o spectra.o lensing.o - -INPUT = input.o - -PRECISION = precision.o - -BACKGROUND = background.o - -THERMO = thermodynamics.o - -PERTURBATIONS = perturbations.o - -TRANSFER = transfer.o - -PRIMORDIAL = primordial.o - -SPECTRA = spectra.o - -NONLINEAR = nonlinear.o - -LENSING = lensing.o - -OUTPUT = output.o - -CLASS = class.o - -TEST_LOOPS = test_loops.o - -TEST_LOOPS_OMP = test_loops_omp.o - -TEST_DEGENERACY = test_degeneracy.o - -TEST_TRANSFER = test_transfer.o - -TEST_NONLINEAR = test_nonlinear.o - -TEST_PERTURBATIONS = test_perturbations.o - -TEST_THERMODYNAMICS = test_thermodynamics.o - -TEST_BACKGROUND = test_background.o - -TEST_SIGMA = test_sigma.o - -TEST_HYPERSPHERICAL = test_hyperspherical.o - -TEST_STEPHANE = test_stephane.o - -C_TOOLS = $(addprefix tools/, $(addsuffix .c,$(basename $(TOOLS)))) -C_SOURCE = $(addprefix source/, $(addsuffix .c,$(basename $(SOURCE) $(OUTPUT)))) -C_TEST = $(addprefix test/, $(addsuffix .c,$(basename $(TEST_DEGENERACY) $(TEST_LOOPS) $(TEST_TRANSFER) $(TEST_NONLINEAR) $(TEST_PERTURBATIONS) $(TEST_THERMODYNAMICS)))) -C_MAIN = $(addprefix main/, $(addsuffix .c,$(basename $(CLASS)))) -C_ALL = $(C_MAIN) $(C_TOOLS) $(C_SOURCE) -H_ALL = $(addprefix include/, common.h svnversion.h $(addsuffix .h, $(basename $(notdir $(C_ALL))))) -PRE_ALL = cl_ref.pre clt_permille.pre -INI_ALL = explanatory.ini lcdm.ini -MISC_FILES = Makefile CPU psd_FD_single.dat myselection.dat myevolution.dat README bbn/sBBN.dat external_Pk/* cpp -PYTHON_FILES = python/classy.pyx python/setup.py python/cclassy.pxd python/test_class.py - - - - -all: libclass.a -#all: class - -# libclass.a: $(TOOLS) $(SOURCE) $(EXTERNAL) -# $(AR) $@ $(addprefix build/, $(TOOLS) $(SOURCE) $(EXTERNAL)) - -libclass.a: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(CLASS) - $(AR) $@ $(addprefix build/, $(TOOLS) $(SOURCE) $(EXTERNAL)) - -class: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(CLASS) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o class $(addprefix build/,$(notdir $^)) -lm - -test_sigma: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_SIGMA) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o test_sigma $(addprefix build/,$(notdir $^)) -lm - -test_loops: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_LOOPS) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_loops_omp: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_LOOPS_OMP) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_stephane: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_STEPHANE) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_degeneracy: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_DEGENERACY) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_transfer: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_TRANSFER) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_nonlinear: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_NONLINEAR) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_perturbations: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_PERTURBATIONS) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_thermodynamics: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_THERMODYNAMICS) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_background: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_BACKGROUND) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm - -test_hyperspherical: $(TOOLS) $(TEST_HYPERSPHERICAL) - $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o test_hyperspherical $(addprefix build/,$(notdir $^)) -lm - - -tar: $(C_ALL) $(C_TEST) $(H_ALL) $(PRE_ALL) $(INI_ALL) $(MISC_FILES) $(HYREC) $(PYTHON_FILES) - tar czvf class.tar.gz $(C_ALL) $(H_ALL) $(PRE_ALL) $(INI_ALL) $(MISC_FILES) $(HYREC) $(PYTHON_FILES) - -classy: libclass.a python/classy.pyx python/cclassy.pxd - cd python; export CC=$(CC); $(PYTHON) setup.py install $(PYTHONFLAGS) - -clean: .base - rm -rf $(WRKDIR); - rm -f libclass.a - rm -f $(MDIR)/python/classy.c - rm -rf $(MDIR)/python/build +#Some Makefile for CLASS. +#Julien Lesgourgues, 28.11.2011 + +MDIR := $(shell pwd) +WRKDIR = $(MDIR)/build + +.base: + if ! [ -e $(WRKDIR) ]; then mkdir $(WRKDIR) ; mkdir $(WRKDIR)/lib; fi; + touch build/.base + +vpath %.c source:tools:main:test +vpath %.o build +vpath .base build + +######################################################## +###### LINES TO ADAPT TO YOUR PLATEFORM ################ +######################################################## + +# your C compiler: +CC = gcc +#CC = icc +#CC = pgcc + +# your tool for creating static libraries: +AR = ar rv + +# Your python interpreter. +# In order to use Python 3, you can manually +# substitute python3 to python in the line below, or you can simply +# add a compilation option on the terminal command line: +# "PYTHON=python3 make all" (THanks to Marius Millea for pyhton3 +# compatibility) +PYTHON ?= python + +# your optimization flag +#OPTFLAG = -O4 -ffast-math #-march=native +#OPTFLAG = -Ofast -ffast-math #-march=native +#OPTFLAG = -fast +OPTFLAG = -O4 -ffast-math -lgsl -lgslcblas + +# your openmp flag (comment for compiling without openmp) +OMPFLAG = -fopenmp +#OMPFLAG = -mp -mp=nonuma -mp=allcores -g +#OMPFLAG = -openmp + +# all other compilation flags +CCFLAG = -g -fPIC +LDFLAG = -g -fPIC + +# leave blank to compile without HyRec, or put path to HyRec directory +# (with no slash at the end: e.g. hyrec or ../hyrec) +HYREC = hyrec + +######################################################## +###### IN PRINCIPLE THE REST SHOULD BE LEFT UNCHANGED ## +######################################################## + +# pass current working directory to the code +CCFLAG += -D__CLASSDIR__='"$(MDIR)"' + +# where to find include files *.h +INCLUDES = -I../include + +# automatically add external programs if needed. First, initialize to blank. +EXTERNAL = + +# eventually update flags for including HyRec +ifneq ($(HYREC),) +vpath %.c $(HYREC) +CCFLAG += -DHYREC +#LDFLAGS += -DHYREC +INCLUDES += -I../hyrec +EXTERNAL += hyrectools.o helium.o hydrogen.o history.o +endif + +%.o: %.c .base + cd $(WRKDIR);$(CC) $(OPTFLAG) $(OMPFLAG) $(CCFLAG) $(INCLUDES) -c ../$< -o $*.o + +TOOLS = growTable.o dei_rkck.o sparse.o evolver_rkck.o evolver_ndf15.o arrays.o parser.o quadrature.o hyperspherical.o common.o trigonometric_integrals.o + +SOURCE = input.o background.o thermodynamics.o perturbations.o primordial.o nonlinear.o transfer.o spectra.o lensing.o + +INPUT = input.o + +PRECISION = precision.o + +BACKGROUND = background.o + +THERMO = thermodynamics.o + +PERTURBATIONS = perturbations.o + +TRANSFER = transfer.o + +PRIMORDIAL = primordial.o + +SPECTRA = spectra.o + +NONLINEAR = nonlinear.o + +LENSING = lensing.o + +OUTPUT = output.o + +CLASS = class.o + +TEST_LOOPS = test_loops.o + +TEST_LOOPS_OMP = test_loops_omp.o + +TEST_DEGENERACY = test_degeneracy.o + +TEST_SPECTRA = test_spectra.o + +TEST_TRANSFER = test_transfer.o + +TEST_NONLINEAR = test_nonlinear.o + +TEST_PERTURBATIONS = test_perturbations.o + +TEST_THERMODYNAMICS = test_thermodynamics.o + +TEST_BACKGROUND = test_background.o + +TEST_SIGMA = test_sigma.o + +TEST_HYPERSPHERICAL = test_hyperspherical.o + +TEST_STEPHANE = test_stephane.o + +C_TOOLS = $(addprefix tools/, $(addsuffix .c,$(basename $(TOOLS)))) +C_SOURCE = $(addprefix source/, $(addsuffix .c,$(basename $(SOURCE) $(OUTPUT)))) +C_TEST = $(addprefix test/, $(addsuffix .c,$(basename $(TEST_DEGENERACY) $(TEST_LOOPS) $(TEST_TRANSFER) $(TEST_NONLINEAR) $(TEST_PERTURBATIONS) $(TEST_THERMODYNAMICS)))) +C_MAIN = $(addprefix main/, $(addsuffix .c,$(basename $(CLASS)))) +C_ALL = $(C_MAIN) $(C_TOOLS) $(C_SOURCE) +H_ALL = $(addprefix include/, common.h svnversion.h $(addsuffix .h, $(basename $(notdir $(C_ALL))))) +PRE_ALL = cl_ref.pre clt_permille.pre +INI_ALL = explanatory.ini lcdm.ini +MISC_FILES = Makefile CPU psd_FD_single.dat myselection.dat myevolution.dat README bbn/sBBN.dat external_Pk/* cpp +PYTHON_FILES = python/classy.pyx python/setup.py python/cclassy.pxd python/test_class.py + +all: libclass.a + +#libclass.a: $(TOOLS) $(SOURCE) $(EXTERNAL) +# $(AR) $@ $(addprefix build/, $(TOOLS) $(SOURCE) $(EXTERNAL)) +libclass.a: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(CLASS) + $(AR) $@ $(addprefix build/, $(TOOLS) $(SOURCE) $(EXTERNAL)) + + + +class: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(CLASS) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o class $(addprefix build/,$(notdir $^)) -lm + +test_sigma: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_SIGMA) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o test_sigma $(addprefix build/,$(notdir $^)) -lm + +test_loops: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_LOOPS) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_loops_omp: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_LOOPS_OMP) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_stephane: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_STEPHANE) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_degeneracy: $(TOOLS) $(SOURCE) $(EXTERNAL) $(OUTPUT) $(TEST_DEGENERACY) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_spectra: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_SPECTRA) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_transfer: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_TRANSFER) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_nonlinear: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_NONLINEAR) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_perturbations: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_PERTURBATIONS) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_thermodynamics: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_THERMODYNAMICS) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_background: $(TOOLS) $(SOURCE) $(EXTERNAL) $(TEST_BACKGROUND) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o $@ $(addprefix build/,$(notdir $^)) -lm + +test_hyperspherical: $(TOOLS) $(TEST_HYPERSPHERICAL) + $(CC) $(OPTFLAG) $(OMPFLAG) $(LDFLAG) -o test_hyperspherical $(addprefix build/,$(notdir $^)) -lm + + +tar: $(C_ALL) $(C_TEST) $(H_ALL) $(PRE_ALL) $(INI_ALL) $(MISC_FILES) $(HYREC) $(PYTHON_FILES) + tar czvf class.tar.gz $(C_ALL) $(H_ALL) $(PRE_ALL) $(INI_ALL) $(MISC_FILES) $(HYREC) $(PYTHON_FILES) + +classy: libclass.a python/classy.pyx python/cclassy.pxd +ifdef OMPFLAG + cp python/setup.py python/autosetup.py +else + grep -v "lgomp" python/setup.py > python/autosetup.py +endif + cd python; export CC='$(CC) $(OPTFLAG)'; $(PYTHON) autosetup.py install || $(PYTHON) autosetup.py install --user + rm python/autosetup.py + +clean: .base + rm -rf $(WRKDIR); + rm -f libclass.a + rm -f $(MDIR)/python/classy.c + rm -rf $(MDIR)/python/build diff --git a/class/README.md b/class/README.md new file mode 100644 index 00000000..0307968e --- /dev/null +++ b/class/README.md @@ -0,0 +1,118 @@ +CLASS: Cosmic Linear Anisotropy Solving System {#mainpage} +============================================== + +Authors: Julien Lesgourgues and Thomas Tram + +with several major inputs from other people, especially Benjamin +Audren, Simon Prunet, Jesus Torrado, Miguel Zumalacarregui, Francesco +Montanari, etc. + +For download and information, see http://class-code.net + + +Compiling CLASS and getting started +----------------------------------- + +(the information below can also be found on the webpage, just below +the download button) + +Download the code from the webpage and unpack the archive (tar -zxvf +class_vx.y.z.tar.gz), or clone it from +https://github.com/lesgourg/class_public. Go to the class directory +(cd class/ or class_public/ or class_vx.y.z/) and compile (make clean; +make class). You can usually speed up compilation with the option -j: +make -j class. If the first compilation attempt fails, you may need to +open the Makefile and adapt the name of the compiler (default: gcc), +of the optimization flag (default: -O4 -ffast-math) and of the OpenMP +flag (default: -fopenmp; this flag is facultative, you are free to +compile without OpenMP if you don't want parallel execution; note that +you need the version 4.2 or higher of gcc to be able to compile with +-fopenmp). Many more details on the CLASS compilation are given on the +wiki page + +https://github.com/lesgourg/class_public/wiki/Installation + +(in particular, for compiling on Mac >= 10.9 despite of the clang +incompatibility with OpenMP). + +To check that the code runs, type: + + ./class explanatory.ini + +The explanatory.ini file is THE reference input file, containing and +explaining the use of all possible input parameters. We recommend to +read it, to keep it unchanged (for future reference), and to create +for your own purposes some shorter input files, containing only the +input lines which are useful for you. Input files must have a *.ini +extension. + +If you want to play with the precision/speed of the code, you can use +one of the provided precision files (e.g. cl_permille.pre) or modify +one of them, and run with two input files, for instance: + + ./class test.ini cl_permille.pre + +The files *.pre are suppposed to specify the precision parameters for +which you don't want to keep default values. If you find it more +convenient, you can pass these precision parameter values in your *.ini +file instead of an additional *.pre file. + +The automatically-generated documentation is located in + + doc/manual/html/index.html + doc/manual/CLASS_manual.pdf + +On top of that, if you wish to modify the code, you will find lots of +comments directly in the files. + +Python +------ + +To use CLASS from python, or ipython notebooks, or from the Monte +Python parameter extraction code, you need to compile not only the +code, but also its python wrapper. This can be done by typing just +'make' instead of 'make class' (or for speeding up: 'make -j'). More +details on the wrapper and its compilation are found on the wiki page + +https://github.com/lesgourg/class_public/wiki + +Plotting utility +---------------- + +Since version 2.3, the package includes an improved plotting script +called CPU.py (Class Plotting Utility), written by Benjamin Audren and +Jesus Torrado. It can plot the Cl's, the P(k) or any other CLASS +output, for one or several models, as well as their ratio or percentage +difference. The syntax and list of available options is obtained by +typing 'pyhton CPU.py -h'. There is a similar script for MATLAB, +written by Thomas Tram. To use it, once in MATLAB, type 'help +plot_CLASS_output.m' + +Developing the code +-------------------- + +If you want to develop the code, we suggest that you download it from +the github webpage + +https://github.com/lesgourg/class_public + +rather than from class-code.net. Then you will enjoy all the feature +of git repositories. You can even develop your own branch and get it +merged to the public distribution. For related instructions, check + +https://github.com/lesgourg/class_public/wiki/Public-Contributing + +Using the code +-------------- + +You can use CLASS freely, provided that in your publications, you cite +at least the paper `CLASS II: Approximation schemes `. Feel free to cite more CLASS papers! + +Support +------- + +To get support, please open a new issue on the + +https://github.com/lesgourg/class_public + +webpage! diff --git a/class/RealSpaceInterface/Calc2D/CalculationClass.py b/class/RealSpaceInterface/Calc2D/CalculationClass.py new file mode 100644 index 00000000..0a6b5bb4 --- /dev/null +++ b/class/RealSpaceInterface/Calc2D/CalculationClass.py @@ -0,0 +1,187 @@ +import os +import logging + +import cv2 +import numpy as np + +from classy import Class + +from Calc2D.TransferFunction import ComputeTransferFunctionList +from Calc2D.DataGeneration import GenerateGaussianData, GenerateSIData +from Calc2D.DataPropagation import PropagateDatawithList +from Calc2D.rFourier import * +from Calc2D.Database import Database +from collections import namedtuple + +import config + +ClSpectrum = namedtuple("Cls", ["l", "tCl"]) +PkSpectrum = namedtuple("Pkh", ["kh", "Pkh"]) + +def normalize(real): + """ + Given the `real` data, i.e. either a 2d array or a flattened 1d array + of the relative density perturbations, normalize its values as follows: + + The client expects the values to be in the interval of [-1, 1]. + Take a symmetric interval around a `real` value of 0 and linearly + map it to the required interval [-1, 1]. + """ + minimum, maximum = real.min(), real.max() + bound = max(abs(maximum), abs(minimum)) + result = real / bound + return result + +class Calculation(object): + def __init__(self, + kbins, + resolution = 200, + gauge="newtonian", + kperdecade=200, + P_k_max=100, + evolver=1): + # also sets `endshape` through setter + self.resolution = resolution + self.gauge = gauge + self.evolver = evolver + self.P_k_max = P_k_max + self.kperdecade = kperdecade + + self.redshift = None # to be set later + self.size = None # to be set later + + self.krange = np.logspace(-4, 1, kbins) + + @property + def resolution(self): + return self._resolution + + @resolution.setter + def resolution(self, resolution): + self._resolution = resolution + self.endshape = (resolution, resolution) + + def getData(self, redshiftindex): + FValuenew = PropagateDatawithList( + k=self.k, + FValue=self.FValue, + zredindex=redshiftindex, + transferFunctionlist=self.TransferFunctionList) + + Valuenew = dict() + FValue_abs = np.abs(self.FValue) + _min, _max = FValue_abs.min(), FValue_abs.max() + dimensions = (self.endshape[0] / 2, self.endshape[1]) + for quantity, FT in FValuenew.items(): + FT_abs = np.abs(FT) + FT_normalized = cv2.resize(FT_abs, dimensions).ravel() + FT_normalized = (FT_normalized - _min) / (_max - _min) + real = realInverseFourier(FT.reshape(self.FValue.shape)) + # real = cv2.resize(real, self.endshape).ravel() + real = real.ravel() + + minimum, maximum = real.min(), real.max() + Valuenew[quantity] = normalize(real) + + return Valuenew, FValuenew, (minimum, maximum) + + + def getInitialData(self): + # for odd values of self._resolution, this is necessary + Value = cv2.resize(realInverseFourier(self.FValue), self.endshape) + + minimum, maximum = Value.min(), Value.max() + Value = normalize(Value) + + assert Value.size == self.resolution ** 2 + + return Value.ravel(), cv2.resize( + (np.abs(self.FValue) - np.abs(self.FValue).min()) / + (np.abs(self.FValue).max() - np.abs(self.FValue).min()), + (self.endshape[0] / 2, self.endshape[1])).ravel(), (minimum, + maximum) + + def getTransferData(self, redshiftindex): + return {field: transfer_function[redshiftindex](self.krange) for field, transfer_function in self.TransferFunctionList.items()}, self.krange + + def setCosmologialParameters(self, cosmologicalParameters): + self.cosmologicalParameters = cosmologicalParameters + + # Calculate transfer functions + self.TransferFunctionList = ComputeTransferFunctionList(self.cosmologicalParameters, self.redshift) + # Calculate Cl's + self.tCl, self.mPk = self.calculate_spectra(self.cosmologicalParameters) + + def calculate_spectra(self, cosmo_params, force_recalc=False): + settings = cosmo_params.copy() + settings.update({ + "output": "tCl,mPk", + "evolver": "1", + "gauge": "newtonian", + "P_k_max_1/Mpc": 10, + }) + + database = Database(config.DATABASE_DIR, "spectra.dat") + + if settings in database and not force_recalc: + data = database[settings] + ell = data["ell"] + tt = data["tt"] + kh = data["kh"] + Pkh = data["Pkh"] + self.z_rec = data["z_rec"] + else: + cosmo = Class() + cosmo.set(settings) + cosmo.compute() + # Cl's + data = cosmo.raw_cl() + ell = data["ell"] + tt = data["tt"] + # Matter spectrum + k = np.logspace(-3, 1, config.MATTER_SPECTRUM_CLIENT_SAMPLES_PER_DECADE * 4) + Pk = np.vectorize(cosmo.pk)(k, 0) + kh = k * cosmo.h() + Pkh = Pk / cosmo.h()**3 + # Get redshift of decoupling + z_rec = cosmo.get_current_derived_parameters(['z_rec'])['z_rec'] + self.z_rec = z_rec + # Store to database + database[settings] = { + "ell": data["ell"], + "tt": data["tt"], + + "kh": k, + "Pkh": Pk, + + "z_rec": z_rec, + } + + return ClSpectrum(ell[2:], tt[2:]), PkSpectrum(kh, Pkh) + + @property + def z_dec(self): + if self.z_rec is None: + raise ValueError("z_rec hasn't been computed yet") + return self.z_rec + + def setInitialConditions(self, + A=1, + sigma=2, + initialDataType="SI", + SIlimit=None, + SI_ns=0.96): + logging.info("Generating Initial Condition") + + if initialDataType == "Gaussian": + self.ValueE, self.FValue, self.k, self.kxE, self.kyE = GenerateGaussianData( + sigma, self.size, self.resolution) + elif initialDataType == "SI": + self.ValueE, self.FValue, self.k, self.kxE, self.kyE = GenerateSIData( + A, + self.size, + self.resolution, + limit=SIlimit, + ns=SI_ns) + else: + logging.warn("initialDataType " + str(initialDataType) + " not found") diff --git a/class/RealSpaceInterface/Calc2D/DataGeneration.py b/class/RealSpaceInterface/Calc2D/DataGeneration.py new file mode 100644 index 00000000..7e2c2b44 --- /dev/null +++ b/class/RealSpaceInterface/Calc2D/DataGeneration.py @@ -0,0 +1,91 @@ +import logging + +import numpy as np +import cv2 + +from Calc2D.rFourier import realFourier, realInverseFourier + +def GenerateGaussianData(sigma, size, points, A=1): + xr = np.linspace(-size / 2.0, size / 2.0, points) + yr = np.linspace(-size / 2.0, size / 2.0, points) + step = xr[1] - xr[0] + x, y = np.meshgrid( + xr, yr, indexing='ij', sparse=True) # indexing is important + del xr, yr + + #use the more easy formula + Value = A * np.exp(-(x**2 + y**2) / (2 * sigma**2)) + + kx, ky, FValue = realFourier(step, Value) + kxr, kyr = np.meshgrid(kx, ky, indexing='ij', sparse=True) + + k = np.sqrt(kxr**2 + kyr**2) + del kxr, kyr + + kx = (min(kx), max(kx)) #just return the extremal values to save memory + ky = (min(ky), max(ky)) + + ValueE = (Value.min(), Value.max()) + + return ValueE, FValue, k, kx, ky + +def GenerateSIData(A, size, points, limit=None, ns=0.96): + xr = np.linspace(-size / 2.0, size / 2.0, points) + yr = np.linspace(-size / 2.0, size / 2.0, points) + step = xr[1] - xr[0] + + x, y = np.meshgrid( + xr, yr, indexing='ij', sparse=True) # indexing is important + del xr, yr + Value = 0 * x + 0 * y + + kx, ky, FValue = realFourier(step, Value) #FValue==0 + + kxr, kyr = np.meshgrid(kx, ky, indexing='ij', sparse=True) + + k = np.sqrt(kxr**2 + kyr**2) + del kxr, kyr + + if limit == None: + + ktilde = k.flatten() + ktilde[np.argmin(k)] = 10**9 #just let the background be arbitrary low + ktilde = ktilde.reshape(k.shape) + + FValue = np.random.normal( + loc=0, + scale=np.sqrt(A / ktilde**( + 2 - (ns - 1) * 2. / 3.)) / np.sqrt(2)) + np.random.normal( + loc=0, + scale=np.sqrt(A / ktilde** + (2 - (ns - 1) * 2. / 3.)) / np.sqrt(2)) * 1j + + elif type(limit) == list or type(limit) == tuple: + + iunder, junder = np.where(k < limit[1]) + + for t in range(len(iunder)): + + if k[iunder[t]][junder[t]] > limit[0] and k[iunder[t]][junder[t]] > 0: + + FValue[iunder[t]][junder[t]] = np.random.normal( + loc=0, + scale=np.sqrt(A / k[iunder[t]][junder[t]]** + (2 - (ns - 1) * 2. / 3.)) / + np.sqrt(2)) + np.random.normal( + loc=0, + scale=np.sqrt(A / k[iunder[t]][junder[t]]** + (2 - + (ns - 1) * 2. / 3.)) / np.sqrt(2)) * 1j + + else: + raise ValueError("limit must be None or tuple or list") + + Value = realInverseFourier(FValue) + + kx = (min(kx), max(kx)) + ky = (min(ky), max(ky)) + + ValueE = (Value.min(), Value.max()) + + return ValueE, FValue, k, kx, ky diff --git a/class/RealSpaceInterface/Calc2D/DataPropagation.py b/class/RealSpaceInterface/Calc2D/DataPropagation.py new file mode 100644 index 00000000..83bca8e8 --- /dev/null +++ b/class/RealSpaceInterface/Calc2D/DataPropagation.py @@ -0,0 +1,37 @@ +import numpy as np +#uses one dimensional interpolation +def PropagateDatawithListOld(k,FValue,zredindex,transferFunctionlist): + return (transferFunctionlist[zredindex](k.ravel()) * FValue.ravel()).reshape(FValue.shape) + +def PropagateDatawithList(k, FValue, zredindex, transferFunctionlist): + result = {} + for field, transfer_function in transferFunctionlist.items(): + result[field] = (transfer_function[zredindex](k.ravel()) * FValue.ravel()).reshape(FValue.shape) + return result + +#module with uses two dimensional interpolation and propagates all data at once (fastest but high memory consumption) +def PropagateAllData(k,FValue,allzred,transferFunction): + + allFValue = np.ones((len(allzred),FValue.shape[0],FValue.shape[1]),dtype=complex) + + for kxindex in range(FValue.shape[0]): + allFValue[:,kxindex,:] = transferFunction(allzred,k[kxindex])*FValue[kxindex] + + + return allFValue + + +#module with uses 2 dimensional interpolation (slowest but can be useful if the set of redshift changes very often) +def PropagateData(k,FValue,zred,transferFunction): + + FValuenew = np.ones(FValue.shape,dtype=complex) + + for kxindex in range(FValue.shape[0]): + allFValue[kxindex,:] = transferFunction(zred,k[kxindex])*FValue[kxindex] + + + return allFValue + + + + diff --git a/class/RealSpaceInterface/Calc2D/Database.py b/class/RealSpaceInterface/Calc2D/Database.py new file mode 100644 index 00000000..bc8f006c --- /dev/null +++ b/class/RealSpaceInterface/Calc2D/Database.py @@ -0,0 +1,58 @@ +import pickle +import os +import logging +import uuid + +class Database: + def __init__(self, directory, db_file="database.dat"): + self.directory = directory + self.db_file = db_file + + if not os.path.isdir(directory): + raise ValueError("'{}' is not a directory!".format(directory)) + + self.db_path = os.path.join(directory, db_file) + if not os.path.exists(self.db_path): + logging.info("No database found; Creating one at {}.".format(self.db_path)) + with open(self.db_path, "w") as f: + pickle.dump(dict(), f) + + self.db = self.__read_database() + + def __read_database(self): + with open(self.db_path) as f: + return pickle.load(f) + + def __write_database(self): + with open(self.db_path, "w") as f: + pickle.dump(self.db, f) + + def __create_file(self, data): + filename = str(uuid.uuid4()) + with open(os.path.join(self.directory, filename), "w") as f: + pickle.dump(data, f) + return filename + + def __get_frozen_key(self, key): + return frozenset(key.items()) + + def __getitem__(self, key): + frozen_key = self.__get_frozen_key(key) + if frozen_key in self.db: + filename = self.db[frozen_key] + with open(os.path.join(self.directory, filename)) as f: + return pickle.load(f) + else: + raise KeyError("No data for key: {}".format(key)) + + def __setitem__(self, key, data): + frozen_key = self.__get_frozen_key(key) + self.db[frozen_key] = self.__create_file(data) + self.__write_database() + + def __contains__(self, key): + """ + Return whether `self` contains a record + for the given `key`. + """ + return self.__get_frozen_key(key) in self.db \ No newline at end of file diff --git a/class/RealSpaceInterface/Calc2D/TransferFunction.py b/class/RealSpaceInterface/Calc2D/TransferFunction.py new file mode 100644 index 00000000..8747f007 --- /dev/null +++ b/class/RealSpaceInterface/Calc2D/TransferFunction.py @@ -0,0 +1,64 @@ +import os.path +import pickle +import uuid +import numpy as np +from scipy.interpolate import InterpolatedUnivariateSpline, RectBivariateSpline +import sys +import logging + +from classy import Class + +import Calc2D.Database as Database +import config + +TRANSFER_QUANTITIES = ["d_g", "d_ur", "d_cdm", "d_b", "d_g/4 + psi"] + +def ComputeTransferData(settings, redshift): + database_key = settings.copy() + database_key.update({'redshift': tuple(redshift)}) + + database = Database.Database(config.DATABASE_DIR) + if database_key in database: + return database[database_key], redshift + else: + cosmo = Class() + cosmo.set(settings) + cosmo.compute() + + outputData = [cosmo.get_transfer(z) for z in redshift] + # Calculate d_g/4+psi + for transfer_function_dict in outputData: + transfer_function_dict["d_g/4 + psi"] = transfer_function_dict["d_g"]/4 + transfer_function_dict["psi"] + # Now filter the relevant fields + fields = TRANSFER_QUANTITIES + ["k (h/Mpc)"] + outputData = [{field: outputData[i][field] for field in fields} for i in range(len(redshift))] + + database[database_key] = outputData + return outputData, redshift + + +def ComputeTransferFunctionList(cosmologicalParameters, redshift, kperdecade=200, P_k_max=100): + class_settings = cosmologicalParameters.copy() + class_settings.update({ + "output": "mTk", + "gauge": "newtonian", + "evolver": "1", + "P_k_max_h/Mpc": P_k_max, + "k_per_decade_for_pk": kperdecade, + "z_max_pk": str(max(redshift)), + }) + + data_dict, redshift = ComputeTransferData(class_settings, redshift) + transfer_functions = {field: [] for field in TRANSFER_QUANTITIES} + + + for i in range(len(redshift)): + k_data = data_dict[0]["k (h/Mpc)"] * cosmologicalParameters["h"] #in order to get k [1/Mpc] + k_data_zero = np.concatenate(([0.0], k_data)) + for field in TRANSFER_QUANTITIES: + data = data_dict[i][field] / data_dict[i][field][0] + data_zero = np.concatenate(([1.0], data)) + interpolated_func = InterpolatedUnivariateSpline(k_data_zero, data_zero) + transfer_functions[field].append(interpolated_func) + + return transfer_functions diff --git a/class/RealSpaceInterface/Calc2D/__init__.py b/class/RealSpaceInterface/Calc2D/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/class/RealSpaceInterface/Calc2D/rFourier.py b/class/RealSpaceInterface/Calc2D/rFourier.py new file mode 100644 index 00000000..b8a54378 --- /dev/null +++ b/class/RealSpaceInterface/Calc2D/rFourier.py @@ -0,0 +1,21 @@ +import numpy as np +import numpy.fft as fft + +def realFourier(step, Value): + FValue = np.fft.fftshift( + np.fft.rfft2(Value), axes=(0)) #shifting only the x axes + + kx = np.fft.fftshift(np.fft.fftfreq(Value.shape[0], d=step)) * 2 * np.pi + ky = np.fft.rfftfreq(Value.shape[0], d=step) * 2 * np.pi + + return kx, ky, FValue + +def realInverseFourier(FValue): + return np.fft.irfft2(np.fft.ifftshift( + FValue, axes=(0))) #shifting only on the x axes + + +def realInverseAllFourier(allFValue): + return np.fft.irfftn( + np.fft.ifftshift(allFValue, axes=(1)), + axes=(1, 2)) #shifting only on the x axes diff --git a/class/RealSpaceInterface/README b/class/RealSpaceInterface/README new file mode 100644 index 00000000..4fc84d3e --- /dev/null +++ b/class/RealSpaceInterface/README @@ -0,0 +1,18 @@ +For installation of python packages, run + + pip install -r requirements.txt + +Launch the application with + + python tornadoserver.py + +Then in any browser open the URL + + http://localhost:7777 + +------------------------------------------------------------ + +Cache files are located in cache/, so to clear the cache, run + + rm cache/* + diff --git a/class/RealSpaceInterface/colormap_converter.py b/class/RealSpaceInterface/colormap_converter.py new file mode 100644 index 00000000..2c18b21d --- /dev/null +++ b/class/RealSpaceInterface/colormap_converter.py @@ -0,0 +1,34 @@ +import matplotlib.cm as cm +import matplotlib.pyplot as plt +import numpy as np +from PIL import Image +import os + +OUTPUT_DIR = os.path.join("static", "images", "colormaps") +WIDTH = 512 + +def create_image(cmap, width): + values = np.linspace(0, 1, width) + colors = cmap(values).reshape((1, width, 4)) + image = Image.fromarray(np.uint8(255 * colors)) + return image + +cmap_names = {} +cmap_names['Uniform'] = [ + 'viridis', 'plasma', 'inferno', 'magma'] +cmap_names['Diverging'] = [ + 'seismic', 'RdYlBu', 'Spectral' + ] +cmap_names['Miscellaneous'] = ['jet'] + +if __name__ == "__main__": + for category in cmap_names: + category_dir = os.path.join(OUTPUT_DIR, category) + if not os.path.exists(category_dir): + os.mkdir(category_dir) + for name in cmap_names[category]: + result = create_image(plt.get_cmap(name), width=WIDTH) + output_path = os.path.join(category_dir, "{}.png".format(name)) + print(output_path) + result.save(output_path) + diff --git a/class/RealSpaceInterface/config.py b/class/RealSpaceInterface/config.py new file mode 100644 index 00000000..90e91691 --- /dev/null +++ b/class/RealSpaceInterface/config.py @@ -0,0 +1,23 @@ +import os + +# Default port number to listen on. Can be overriden by passing a port number +# as the first command line argument, e.g. `python tornadoserver.py 1234` +PORT = 7777 + +# Directory to store previously computed transfer functions, spectra etc. in +DATABASE_DIR = "cache" + +# Maximum number of thread pool workers (only required for multi-user usage) +MAX_THREADPOOL_WORKERS = 8 + +# Path of colormap directory relative to the static directory from which +# tornado serves static files +COLORMAP_PATH = os.path.join("images", "colormaps") + +# number of sample points for the transfer function that is displayed +# in the client +TRANSFER_FUNCTION_CLIENT_SAMPLES = 400 + +# number of sample points for the matter spectrum that is displayed +# in the client per decade +MATTER_SPECTRUM_CLIENT_SAMPLES_PER_DECADE = 40 diff --git a/class/RealSpaceInterface/requirements.txt b/class/RealSpaceInterface/requirements.txt new file mode 100644 index 00000000..2f2dc9a6 --- /dev/null +++ b/class/RealSpaceInterface/requirements.txt @@ -0,0 +1,7 @@ +futures>=3.0.2 +numpy>=1.8.2 +scipy>=0.14.0 +tornado>=4.0.2 +opencv-python +# Building the Python bindings of CLASS requires Cython +Cython diff --git a/class/RealSpaceInterface/static/css/custom.css b/class/RealSpaceInterface/static/css/custom.css new file mode 100644 index 00000000..872a731b --- /dev/null +++ b/class/RealSpaceInterface/static/css/custom.css @@ -0,0 +1,189 @@ +body { + margin: 0; + overflow: hidden; +} + +.activityIndicator-active, .activityIndicator-inactive { + border-radius: 50%; + width: 20px; + height: 20px; + display: inline-block; + vertical-align: sub; +} + +.activityIndicator-active { + border: 3px solid #f3f3f3; + border-top: 3px solid #3498db; + animation: spin 2s linear infinite; +} + +.activityIndicator-inactive { + border: 3px solid #444; + display: none; +} + +@keyframes spin { + 0% { transform: rotate(0deg); } + 100% { transform: rotate(360deg); } +} + +td.color-circle-container { + vertical-align: middle; +} + +.color-circle { + width: 24px; + height: 24px; + border-radius: 50%; + margin: auto; +} + +.popover { + max-width: 100%; +} + +.modal { + overflow-y: scroll; +} + +/* PLOTS */ + +#plotWindowContainer { + position: absolute; + top: 50px; + left: 0px; + overflow: hidden; +} + +#plotWindowWrapper { + min-width: 550px; + border-radius: 3px; +} + +.plotWindowWrapperHidden { +} + +.plotWindowWrapperVisible { + padding-top: 10px; + padding-bottom: 10px; + padding-left: 10px; + padding-right: 10px; +} + +.plotWindowHidden, .plotWindowVisible { + overflow-x: hidden; + background-color: rgba(255, 255, 255, 0.8); +} + +.plotWindowHidden { + display: none; + margin: 0px; +} + +.plotWindowVisible { + display: block; + min-height: 200px; +} + +.plotWindowVisible:not(:last-child) { + margin-bottom: 10px; +} + +#plotWindowToggle { + width: 100%; +} + +/* END PLOTS */ + +#aboutLink { + position: absolute; + padding: 5px; + right: 0; + bottom: 0; + text-align: right; + vertical-align: bottom; + border-top-left-radius: 3px; +} + +#statusBar { + position: absolute; + bottom: 0; + left: 0; + padding: 5px; + border-top-right-radius: 3px; +} + +#statusBar p { + margin: 0; + vertical-align: bottom; +} + +.status-bar-item { + display: inline-block; +} + +/* */ +#simulationTable td { + text-align: center; + vertical-align: middle; +} + +#simulationTable th { + text-align: center; + border: none; +} + +.visible-checkbox { + vertical-align: middle; +} + +/* .cmap-preview, .cmap-preview-button { */ +/* } */ + +.cmap-preview { + width: 64px; + height: inherit; + margin-left: 1em; +} + +/* .cmap-preview-button { */ +/* height: 1em; */ +/* vertical-align: middle; */ +/* } */ + +#colormap-selector-button-placeholder { + width: 64px; + display: inline-block; +} + +.colormap-selector-item { + display: flex; + justify-content: space-between; +} + +.scrollable-menu { + height: auto; + max-height: 200px; + overflow-x: hidden; +} + + +/* FIX DAT.GUI */ +.dg .c input[type=text] { + line-height:normal; +} + +.dg .c div { + box-sizing: content-box; +} + +/* END FIX */ + + +#exceptionModalMessage { + white-space: pre; +} + +.modal-lg { + max-width: 900px; +} diff --git a/class/RealSpaceInterface/static/css/timeline.css b/class/RealSpaceInterface/static/css/timeline.css new file mode 100644 index 00000000..e87f469e --- /dev/null +++ b/class/RealSpaceInterface/static/css/timeline.css @@ -0,0 +1,28 @@ +.player { + width: 25%; + border-radius: 2px; + margin-top: 6px; +} + +.timeline { + height: 12px; + /*background: linear-gradient(to right, red 0%, red 20%, green 20%);*/ + border-radius: 8px; + /* horizontal vertical blur spread color */ + /* box-shadow: inset 2px 2px 20px -5px #333; */ + cursor: pointer; +} + +.scrubber { + width: 18px; + height: 18px; + border-radius: 50%; + float: left; + cursor: pointer; + background: linear-gradient(to bottom, hsl(134, 61%, 45%), hsl(134, 61%, 35%)); + box-shadow: 0px 2px 10px 2px #333; +} + +.scrubber:hover { + background: linear-gradient(to bottom, hsl(134, 61%, 65%), hsl(134, 61%, 55%)); +} diff --git a/class/RealSpaceInterface/static/favicon-16x16.png b/class/RealSpaceInterface/static/favicon-16x16.png new file mode 100644 index 00000000..b1eaa217 Binary files /dev/null and b/class/RealSpaceInterface/static/favicon-16x16.png differ diff --git a/class/RealSpaceInterface/static/favicon-32x32.png b/class/RealSpaceInterface/static/favicon-32x32.png new file mode 100644 index 00000000..d343d67a Binary files /dev/null and b/class/RealSpaceInterface/static/favicon-32x32.png differ diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/.gitignore b/class/RealSpaceInterface/static/fonts/open-iconic/.gitignore new file mode 100644 index 00000000..496ee2ca --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/.gitignore @@ -0,0 +1 @@ +.DS_Store \ No newline at end of file diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/FONT-LICENSE b/class/RealSpaceInterface/static/fonts/open-iconic/FONT-LICENSE new file mode 100644 index 00000000..a1dc03f3 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/FONT-LICENSE @@ -0,0 +1,86 @@ +SIL OPEN FONT LICENSE Version 1.1 + +Copyright (c) 2014 Waybury + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/ICON-LICENSE b/class/RealSpaceInterface/static/fonts/open-iconic/ICON-LICENSE new file mode 100644 index 00000000..2199f4a6 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/ICON-LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2014 Waybury + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. \ No newline at end of file diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/README.md b/class/RealSpaceInterface/static/fonts/open-iconic/README.md new file mode 100644 index 00000000..6b810e47 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/README.md @@ -0,0 +1,114 @@ +[Open Iconic v1.1.1](http://useiconic.com/open) +=========== + +### Open Iconic is the open source sibling of [Iconic](http://useiconic.com). It is a hyper-legible collection of 223 icons with a tiny footprint—ready to use with Bootstrap and Foundation. [View the collection](http://useiconic.com/open#icons) + + + +## What's in Open Iconic? + +* 223 icons designed to be legible down to 8 pixels +* Super-light SVG files - 61.8 for the entire set +* SVG sprite—the modern replacement for icon fonts +* Webfont (EOT, OTF, SVG, TTF, WOFF), PNG and WebP formats +* Webfont stylesheets (including versions for Bootstrap and Foundation) in CSS, LESS, SCSS and Stylus formats +* PNG and WebP raster images in 8px, 16px, 24px, 32px, 48px and 64px. + + +## Getting Started + +#### For code samples and everything else you need to get started with Open Iconic, check out our [Icons](http://useiconic.com/open#icons) and [Reference](http://useiconic.com/open#reference) sections. + +### General Usage + +#### Using Open Iconic's SVGs + +We like SVGs and we think they're the way to display icons on the web. Since Open Iconic are just basic SVGs, we suggest you display them like you would any other image (don't forget the `alt` attribute). + +``` +icon name +``` + +#### Using Open Iconic's SVG Sprite + +Open Iconic also comes in a SVG sprite which allows you to display all the icons in the set with a single request. It's like an icon font, without being a hack. + +Adding an icon from an SVG sprite is a little different than what you're used to, but it's still a piece of cake. *Tip: To make your icons easily style able, we suggest adding a general class to the* `` *tag and a unique class name for each different icon in the* `` *tag.* + +``` + + + +``` + +Sizing icons only needs basic CSS. All the icons are in a square format, so just set the `` tag with equal width and height dimensions. + +``` +.icon { + width: 16px; + height: 16px; +} +``` + +Coloring icons is even easier. All you need to do is set the `fill` rule on the `` tag. + +``` +.icon-account-login { + fill: #f00; +} +``` + +To learn more about SVG Sprites, read [Chris Coyier's guide](http://css-tricks.com/svg-sprites-use-better-icon-fonts/). + +#### Using Open Iconic's Icon Font... + + +##### …with Bootstrap + +You can find our Bootstrap stylesheets in `font/css/open-iconic-bootstrap.{css, less, scss, styl}` + + +``` + +``` + + +``` + +``` + +##### …with Foundation + +You can find our Foundation stylesheets in `font/css/open-iconic-foundation.{css, less, scss, styl}` + +``` + +``` + + +``` + +``` + +##### …on its own + +You can find our default stylesheets in `font/css/open-iconic.{css, less, scss, styl}` + +``` + +``` + +``` + +``` + + +## License + +### Icons + +All code (including SVG markup) is under the [MIT License](http://opensource.org/licenses/MIT). + +### Fonts + +All fonts are under the [SIL Licensed](http://scripts.sil.org/cms/scripts/page.php?item_id=OFL_web). diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/bower.json b/class/RealSpaceInterface/static/fonts/open-iconic/bower.json new file mode 100644 index 00000000..fbf96616 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/bower.json @@ -0,0 +1,21 @@ +{ + "name": "open-iconic", + "description": "An open source icon set in SVG, webfont and raster formats", + "version": "1.1.1", + "license": [ + "MIT", + "OFL-1.1" + ], + "homepage": "https://useiconic.com/open", + "repository": { + "type": "git", + "url": "git://github.com/iconic/open-iconic.git" + }, + "main": [ + "./sprite/open-iconic.min.svg" + ], + "ignore": [ + "*.json", + "*.md" + ] +} diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.css b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.css new file mode 100644 index 00000000..56c4e5f3 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.css @@ -0,0 +1,952 @@ +/* Bootstrap */ + +@font-face { + font-family: 'Icons'; + src: url('../fonts/open-iconic.eot'); + src: url('../fonts/open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('../fonts/open-iconic.woff') format('woff'), url('../fonts/open-iconic.ttf') format('truetype'), url('../fonts/open-iconic.otf') format('opentype'), url('../fonts/open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + +.oi { + position: relative; + top: 1px; + display: inline-block; + speak:none; + font-family: 'Icons'; + font-style: normal; + font-weight: normal; + line-height: 1; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} + +.oi:empty:before { + width: 1em; + text-align: center; + box-sizing: content-box; +} + +.oi.oi-align-center:before { + text-align: center; +} + +.oi.oi-align-left:before { + text-align: left; +} + +.oi.oi-align-right:before { + text-align: right; +} + + +.oi.oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} + +.oi.oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); +} + +.oi.oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); +} + + +.oi-account-login:before { + content:'\e000'; +} + +.oi-account-logout:before { + content:'\e001'; +} + +.oi-action-redo:before { + content:'\e002'; +} + +.oi-action-undo:before { + content:'\e003'; +} + +.oi-align-center:before { + content:'\e004'; +} + +.oi-align-left:before { + content:'\e005'; +} + +.oi-align-right:before { + content:'\e006'; +} + +.oi-aperture:before { + content:'\e007'; +} + +.oi-arrow-bottom:before { + content:'\e008'; +} + +.oi-arrow-circle-bottom:before { + content:'\e009'; +} + +.oi-arrow-circle-left:before { + content:'\e00a'; +} + +.oi-arrow-circle-right:before { + content:'\e00b'; +} + +.oi-arrow-circle-top:before { + content:'\e00c'; +} + +.oi-arrow-left:before { + content:'\e00d'; +} + +.oi-arrow-right:before { + content:'\e00e'; +} + +.oi-arrow-thick-bottom:before { + content:'\e00f'; +} + +.oi-arrow-thick-left:before { + content:'\e010'; +} + +.oi-arrow-thick-right:before { + content:'\e011'; +} + +.oi-arrow-thick-top:before { + content:'\e012'; +} + +.oi-arrow-top:before { + content:'\e013'; +} + +.oi-audio-spectrum:before { + content:'\e014'; +} + +.oi-audio:before { + content:'\e015'; +} + +.oi-badge:before { + content:'\e016'; +} + +.oi-ban:before { + content:'\e017'; +} + +.oi-bar-chart:before { + content:'\e018'; +} + +.oi-basket:before { + content:'\e019'; +} + +.oi-battery-empty:before { + content:'\e01a'; +} + +.oi-battery-full:before { + content:'\e01b'; +} + +.oi-beaker:before { + content:'\e01c'; +} + +.oi-bell:before { + content:'\e01d'; +} + +.oi-bluetooth:before { + content:'\e01e'; +} + +.oi-bold:before { + content:'\e01f'; +} + +.oi-bolt:before { + content:'\e020'; +} + +.oi-book:before { + content:'\e021'; +} + +.oi-bookmark:before { + content:'\e022'; +} + +.oi-box:before { + content:'\e023'; +} + +.oi-briefcase:before { + content:'\e024'; +} + +.oi-british-pound:before { + content:'\e025'; +} + +.oi-browser:before { + content:'\e026'; +} + +.oi-brush:before { + content:'\e027'; +} + +.oi-bug:before { + content:'\e028'; +} + +.oi-bullhorn:before { + content:'\e029'; +} + +.oi-calculator:before { + content:'\e02a'; +} + +.oi-calendar:before { + content:'\e02b'; +} + +.oi-camera-slr:before { + content:'\e02c'; +} + +.oi-caret-bottom:before { + content:'\e02d'; +} + +.oi-caret-left:before { + content:'\e02e'; +} + +.oi-caret-right:before { + content:'\e02f'; +} + +.oi-caret-top:before { + content:'\e030'; +} + +.oi-cart:before { + content:'\e031'; +} + +.oi-chat:before { + content:'\e032'; +} + +.oi-check:before { + content:'\e033'; +} + +.oi-chevron-bottom:before { + content:'\e034'; +} + +.oi-chevron-left:before { + content:'\e035'; +} + +.oi-chevron-right:before { + content:'\e036'; +} + +.oi-chevron-top:before { + content:'\e037'; +} + +.oi-circle-check:before { + content:'\e038'; +} + +.oi-circle-x:before { + content:'\e039'; +} + +.oi-clipboard:before { + content:'\e03a'; +} + +.oi-clock:before { + content:'\e03b'; +} + +.oi-cloud-download:before { + content:'\e03c'; +} + +.oi-cloud-upload:before { + content:'\e03d'; +} + +.oi-cloud:before { + content:'\e03e'; +} + +.oi-cloudy:before { + content:'\e03f'; +} + +.oi-code:before { + content:'\e040'; +} + +.oi-cog:before { + content:'\e041'; +} + +.oi-collapse-down:before { + content:'\e042'; +} + +.oi-collapse-left:before { + content:'\e043'; +} + +.oi-collapse-right:before { + content:'\e044'; +} + +.oi-collapse-up:before { + content:'\e045'; +} + +.oi-command:before { + content:'\e046'; +} + +.oi-comment-square:before { + content:'\e047'; +} + +.oi-compass:before { + content:'\e048'; +} + +.oi-contrast:before { + content:'\e049'; +} + +.oi-copywriting:before { + content:'\e04a'; +} + +.oi-credit-card:before { + content:'\e04b'; +} + +.oi-crop:before { + content:'\e04c'; +} + +.oi-dashboard:before { + content:'\e04d'; +} + +.oi-data-transfer-download:before { + content:'\e04e'; +} + +.oi-data-transfer-upload:before { + content:'\e04f'; +} + +.oi-delete:before { + content:'\e050'; +} + +.oi-dial:before { + content:'\e051'; +} + +.oi-document:before { + content:'\e052'; +} + +.oi-dollar:before { + content:'\e053'; +} + +.oi-double-quote-sans-left:before { + content:'\e054'; +} + +.oi-double-quote-sans-right:before { + content:'\e055'; +} + +.oi-double-quote-serif-left:before { + content:'\e056'; +} + +.oi-double-quote-serif-right:before { + content:'\e057'; +} + +.oi-droplet:before { + content:'\e058'; +} + +.oi-eject:before { + content:'\e059'; +} + +.oi-elevator:before { + content:'\e05a'; +} + +.oi-ellipses:before { + content:'\e05b'; +} + +.oi-envelope-closed:before { + content:'\e05c'; +} + +.oi-envelope-open:before { + content:'\e05d'; +} + +.oi-euro:before { + content:'\e05e'; +} + +.oi-excerpt:before { + content:'\e05f'; +} + +.oi-expand-down:before { + content:'\e060'; +} + +.oi-expand-left:before { + content:'\e061'; +} + +.oi-expand-right:before { + content:'\e062'; +} + +.oi-expand-up:before { + content:'\e063'; +} + +.oi-external-link:before { + content:'\e064'; +} + +.oi-eye:before { + content:'\e065'; +} + +.oi-eyedropper:before { + content:'\e066'; +} + +.oi-file:before { + content:'\e067'; +} + +.oi-fire:before { + content:'\e068'; +} + +.oi-flag:before { + content:'\e069'; +} + +.oi-flash:before { + content:'\e06a'; +} + +.oi-folder:before { + content:'\e06b'; +} + +.oi-fork:before { + content:'\e06c'; +} + +.oi-fullscreen-enter:before { + content:'\e06d'; +} + +.oi-fullscreen-exit:before { + content:'\e06e'; +} + +.oi-globe:before { + content:'\e06f'; +} + +.oi-graph:before { + content:'\e070'; +} + +.oi-grid-four-up:before { + content:'\e071'; +} + +.oi-grid-three-up:before { + content:'\e072'; +} + +.oi-grid-two-up:before { + content:'\e073'; +} + +.oi-hard-drive:before { + content:'\e074'; +} + +.oi-header:before { + content:'\e075'; +} + +.oi-headphones:before { + content:'\e076'; +} + +.oi-heart:before { + content:'\e077'; +} + +.oi-home:before { + content:'\e078'; +} + +.oi-image:before { + content:'\e079'; +} + +.oi-inbox:before { + content:'\e07a'; +} + +.oi-infinity:before { + content:'\e07b'; +} + +.oi-info:before { + content:'\e07c'; +} + +.oi-italic:before { + content:'\e07d'; +} + +.oi-justify-center:before { + content:'\e07e'; +} + +.oi-justify-left:before { + content:'\e07f'; +} + +.oi-justify-right:before { + content:'\e080'; +} + +.oi-key:before { + content:'\e081'; +} + +.oi-laptop:before { + content:'\e082'; +} + +.oi-layers:before { + content:'\e083'; +} + +.oi-lightbulb:before { + content:'\e084'; +} + +.oi-link-broken:before { + content:'\e085'; +} + +.oi-link-intact:before { + content:'\e086'; +} + +.oi-list-rich:before { + content:'\e087'; +} + +.oi-list:before { + content:'\e088'; +} + +.oi-location:before { + content:'\e089'; +} + +.oi-lock-locked:before { + content:'\e08a'; +} + +.oi-lock-unlocked:before { + content:'\e08b'; +} + +.oi-loop-circular:before { + content:'\e08c'; +} + +.oi-loop-square:before { + content:'\e08d'; +} + +.oi-loop:before { + content:'\e08e'; +} + +.oi-magnifying-glass:before { + content:'\e08f'; +} + +.oi-map-marker:before { + content:'\e090'; +} + +.oi-map:before { + content:'\e091'; +} + +.oi-media-pause:before { + content:'\e092'; +} + +.oi-media-play:before { + content:'\e093'; +} + +.oi-media-record:before { + content:'\e094'; +} + +.oi-media-skip-backward:before { + content:'\e095'; +} + +.oi-media-skip-forward:before { + content:'\e096'; +} + +.oi-media-step-backward:before { + content:'\e097'; +} + +.oi-media-step-forward:before { + content:'\e098'; +} + +.oi-media-stop:before { + content:'\e099'; +} + +.oi-medical-cross:before { + content:'\e09a'; +} + +.oi-menu:before { + content:'\e09b'; +} + +.oi-microphone:before { + content:'\e09c'; +} + +.oi-minus:before { + content:'\e09d'; +} + +.oi-monitor:before { + content:'\e09e'; +} + +.oi-moon:before { + content:'\e09f'; +} + +.oi-move:before { + content:'\e0a0'; +} + +.oi-musical-note:before { + content:'\e0a1'; +} + +.oi-paperclip:before { + content:'\e0a2'; +} + +.oi-pencil:before { + content:'\e0a3'; +} + +.oi-people:before { + content:'\e0a4'; +} + +.oi-person:before { + content:'\e0a5'; +} + +.oi-phone:before { + content:'\e0a6'; +} + +.oi-pie-chart:before { + content:'\e0a7'; +} + +.oi-pin:before { + content:'\e0a8'; +} + +.oi-play-circle:before { + content:'\e0a9'; +} + +.oi-plus:before { + content:'\e0aa'; +} + +.oi-power-standby:before { + content:'\e0ab'; +} + +.oi-print:before { + content:'\e0ac'; +} + +.oi-project:before { + content:'\e0ad'; +} + +.oi-pulse:before { + content:'\e0ae'; +} + +.oi-puzzle-piece:before { + content:'\e0af'; +} + +.oi-question-mark:before { + content:'\e0b0'; +} + +.oi-rain:before { + content:'\e0b1'; +} + +.oi-random:before { + content:'\e0b2'; +} + +.oi-reload:before { + content:'\e0b3'; +} + +.oi-resize-both:before { + content:'\e0b4'; +} + +.oi-resize-height:before { + content:'\e0b5'; +} + +.oi-resize-width:before { + content:'\e0b6'; +} + +.oi-rss-alt:before { + content:'\e0b7'; +} + +.oi-rss:before { + content:'\e0b8'; +} + +.oi-script:before { + content:'\e0b9'; +} + +.oi-share-boxed:before { + content:'\e0ba'; +} + +.oi-share:before { + content:'\e0bb'; +} + +.oi-shield:before { + content:'\e0bc'; +} + +.oi-signal:before { + content:'\e0bd'; +} + +.oi-signpost:before { + content:'\e0be'; +} + +.oi-sort-ascending:before { + content:'\e0bf'; +} + +.oi-sort-descending:before { + content:'\e0c0'; +} + +.oi-spreadsheet:before { + content:'\e0c1'; +} + +.oi-star:before { + content:'\e0c2'; +} + +.oi-sun:before { + content:'\e0c3'; +} + +.oi-tablet:before { + content:'\e0c4'; +} + +.oi-tag:before { + content:'\e0c5'; +} + +.oi-tags:before { + content:'\e0c6'; +} + +.oi-target:before { + content:'\e0c7'; +} + +.oi-task:before { + content:'\e0c8'; +} + +.oi-terminal:before { + content:'\e0c9'; +} + +.oi-text:before { + content:'\e0ca'; +} + +.oi-thumb-down:before { + content:'\e0cb'; +} + +.oi-thumb-up:before { + content:'\e0cc'; +} + +.oi-timer:before { + content:'\e0cd'; +} + +.oi-transfer:before { + content:'\e0ce'; +} + +.oi-trash:before { + content:'\e0cf'; +} + +.oi-underline:before { + content:'\e0d0'; +} + +.oi-vertical-align-bottom:before { + content:'\e0d1'; +} + +.oi-vertical-align-center:before { + content:'\e0d2'; +} + +.oi-vertical-align-top:before { + content:'\e0d3'; +} + +.oi-video:before { + content:'\e0d4'; +} + +.oi-volume-high:before { + content:'\e0d5'; +} + +.oi-volume-low:before { + content:'\e0d6'; +} + +.oi-volume-off:before { + content:'\e0d7'; +} + +.oi-warning:before { + content:'\e0d8'; +} + +.oi-wifi:before { + content:'\e0d9'; +} + +.oi-wrench:before { + content:'\e0da'; +} + +.oi-x:before { + content:'\e0db'; +} + +.oi-yen:before { + content:'\e0dc'; +} + +.oi-zoom-in:before { + content:'\e0dd'; +} + +.oi-zoom-out:before { + content:'\e0de'; +} diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.less b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.less new file mode 100644 index 00000000..fc3fe341 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.less @@ -0,0 +1,960 @@ +/* Bootstrap */ + +/* Override Bootstrap default variable */ +//@icon-font-path: "../fonts/"; + +@font-face { + font-family: 'Icons'; + src: ~"url('@{icon-font-path}open-iconic.eot')"; + src: ~"url('@{icon-font-path}open-iconic.eot?#iconic-sm') format('embedded-opentype')", + ~"url('@{icon-font-path}open-iconic.woff') format('woff')", + ~"url('@{icon-font-path}open-iconic.ttf') format('truetype')", + ~"url('@{icon-font-path}open-iconic.svg#iconic-sm') format('svg')"; + font-weight: normal; + font-style: normal; +} + +// Catchall baseclass +.oi { + position: relative; + top: 1px; + display: inline-block; + font-family: 'Icons'; + font-style: normal; + font-weight: normal; + line-height: 1; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + + &:empty:before { + width: 1em; + text-align: center; + box-sizing: content-box; + } + + &.oi-align-center:before { + text-align: center; + } + + &.oi-align-left:before { + text-align: left; + } + + &.oi-align-right:before { + text-align: right; + } + + + &.oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); + } + + &.oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); + } + + &.oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); + } +} + + + +.oi-account-login:before { + content:"\e000"; +} + +.oi-account-logout:before { + content:"\e001"; +} + +.oi-action-redo:before { + content:"\e002"; +} + +.oi-action-undo:before { + content:"\e003"; +} + +.oi-align-center:before { + content:"\e004"; +} + +.oi-align-left:before { + content:"\e005"; +} + +.oi-align-right:before { + content:"\e006"; +} + +.oi-aperture:before { + content:"\e007"; +} + +.oi-arrow-bottom:before { + content:"\e008"; +} + +.oi-arrow-circle-bottom:before { + content:"\e009"; +} + +.oi-arrow-circle-left:before { + content:"\e00a"; +} + +.oi-arrow-circle-right:before { + content:"\e00b"; +} + +.oi-arrow-circle-top:before { + content:"\e00c"; +} + +.oi-arrow-left:before { + content:"\e00d"; +} + +.oi-arrow-right:before { + content:"\e00e"; +} + +.oi-arrow-thick-bottom:before { + content:"\e00f"; +} + +.oi-arrow-thick-left:before { + content:"\e010"; +} + +.oi-arrow-thick-right:before { + content:"\e011"; +} + +.oi-arrow-thick-top:before { + content:"\e012"; +} + +.oi-arrow-top:before { + content:"\e013"; +} + +.oi-audio-spectrum:before { + content:"\e014"; +} + +.oi-audio:before { + content:"\e015"; +} + +.oi-badge:before { + content:"\e016"; +} + +.oi-ban:before { + content:"\e017"; +} + +.oi-bar-chart:before { + content:"\e018"; +} + +.oi-basket:before { + content:"\e019"; +} + +.oi-battery-empty:before { + content:"\e01a"; +} + +.oi-battery-full:before { + content:"\e01b"; +} + +.oi-beaker:before { + content:"\e01c"; +} + +.oi-bell:before { + content:"\e01d"; +} + +.oi-bluetooth:before { + content:"\e01e"; +} + +.oi-bold:before { + content:"\e01f"; +} + +.oi-bolt:before { + content:"\e020"; +} + +.oi-book:before { + content:"\e021"; +} + +.oi-bookmark:before { + content:"\e022"; +} + +.oi-box:before { + content:"\e023"; +} + +.oi-briefcase:before { + content:"\e024"; +} + +.oi-british-pound:before { + content:"\e025"; +} + +.oi-browser:before { + content:"\e026"; +} + +.oi-brush:before { + content:"\e027"; +} + +.oi-bug:before { + content:"\e028"; +} + +.oi-bullhorn:before { + content:"\e029"; +} + +.oi-calculator:before { + content:"\e02a"; +} + +.oi-calendar:before { + content:"\e02b"; +} + +.oi-camera-slr:before { + content:"\e02c"; +} + +.oi-caret-bottom:before { + content:"\e02d"; +} + +.oi-caret-left:before { + content:"\e02e"; +} + +.oi-caret-right:before { + content:"\e02f"; +} + +.oi-caret-top:before { + content:"\e030"; +} + +.oi-cart:before { + content:"\e031"; +} + +.oi-chat:before { + content:"\e032"; +} + +.oi-check:before { + content:"\e033"; +} + +.oi-chevron-bottom:before { + content:"\e034"; +} + +.oi-chevron-left:before { + content:"\e035"; +} + +.oi-chevron-right:before { + content:"\e036"; +} + +.oi-chevron-top:before { + content:"\e037"; +} + +.oi-circle-check:before { + content:"\e038"; +} + +.oi-circle-x:before { + content:"\e039"; +} + +.oi-clipboard:before { + content:"\e03a"; +} + +.oi-clock:before { + content:"\e03b"; +} + +.oi-cloud-download:before { + content:"\e03c"; +} + +.oi-cloud-upload:before { + content:"\e03d"; +} + +.oi-cloud:before { + content:"\e03e"; +} + +.oi-cloudy:before { + content:"\e03f"; +} + +.oi-code:before { + content:"\e040"; +} + +.oi-cog:before { + content:"\e041"; +} + +.oi-collapse-down:before { + content:"\e042"; +} + +.oi-collapse-left:before { + content:"\e043"; +} + +.oi-collapse-right:before { + content:"\e044"; +} + +.oi-collapse-up:before { + content:"\e045"; +} + +.oi-command:before { + content:"\e046"; +} + +.oi-comment-square:before { + content:"\e047"; +} + +.oi-compass:before { + content:"\e048"; +} + +.oi-contrast:before { + content:"\e049"; +} + +.oi-copywriting:before { + content:"\e04a"; +} + +.oi-credit-card:before { + content:"\e04b"; +} + +.oi-crop:before { + content:"\e04c"; +} + +.oi-dashboard:before { + content:"\e04d"; +} + +.oi-data-transfer-download:before { + content:"\e04e"; +} + +.oi-data-transfer-upload:before { + content:"\e04f"; +} + +.oi-delete:before { + content:"\e050"; +} + +.oi-dial:before { + content:"\e051"; +} + +.oi-document:before { + content:"\e052"; +} + +.oi-dollar:before { + content:"\e053"; +} + +.oi-double-quote-sans-left:before { + content:"\e054"; +} + +.oi-double-quote-sans-right:before { + content:"\e055"; +} + +.oi-double-quote-serif-left:before { + content:"\e056"; +} + +.oi-double-quote-serif-right:before { + content:"\e057"; +} + +.oi-droplet:before { + content:"\e058"; +} + +.oi-eject:before { + content:"\e059"; +} + +.oi-elevator:before { + content:"\e05a"; +} + +.oi-ellipses:before { + content:"\e05b"; +} + +.oi-envelope-closed:before { + content:"\e05c"; +} + +.oi-envelope-open:before { + content:"\e05d"; +} + +.oi-euro:before { + content:"\e05e"; +} + +.oi-excerpt:before { + content:"\e05f"; +} + +.oi-expand-down:before { + content:"\e060"; +} + +.oi-expand-left:before { + content:"\e061"; +} + +.oi-expand-right:before { + content:"\e062"; +} + +.oi-expand-up:before { + content:"\e063"; +} + +.oi-external-link:before { + content:"\e064"; +} + +.oi-eye:before { + content:"\e065"; +} + +.oi-eyedropper:before { + content:"\e066"; +} + +.oi-file:before { + content:"\e067"; +} + +.oi-fire:before { + content:"\e068"; +} + +.oi-flag:before { + content:"\e069"; +} + +.oi-flash:before { + content:"\e06a"; +} + +.oi-folder:before { + content:"\e06b"; +} + +.oi-fork:before { + content:"\e06c"; +} + +.oi-fullscreen-enter:before { + content:"\e06d"; +} + +.oi-fullscreen-exit:before { + content:"\e06e"; +} + +.oi-globe:before { + content:"\e06f"; +} + +.oi-graph:before { + content:"\e070"; +} + +.oi-grid-four-up:before { + content:"\e071"; +} + +.oi-grid-three-up:before { + content:"\e072"; +} + +.oi-grid-two-up:before { + content:"\e073"; +} + +.oi-hard-drive:before { + content:"\e074"; +} + +.oi-header:before { + content:"\e075"; +} + +.oi-headphones:before { + content:"\e076"; +} + +.oi-heart:before { + content:"\e077"; +} + +.oi-home:before { + content:"\e078"; +} + +.oi-image:before { + content:"\e079"; +} + +.oi-inbox:before { + content:"\e07a"; +} + +.oi-infinity:before { + content:"\e07b"; +} + +.oi-info:before { + content:"\e07c"; +} + +.oi-italic:before { + content:"\e07d"; +} + +.oi-justify-center:before { + content:"\e07e"; +} + +.oi-justify-left:before { + content:"\e07f"; +} + +.oi-justify-right:before { + content:"\e080"; +} + +.oi-key:before { + content:"\e081"; +} + +.oi-laptop:before { + content:"\e082"; +} + +.oi-layers:before { + content:"\e083"; +} + +.oi-lightbulb:before { + content:"\e084"; +} + +.oi-link-broken:before { + content:"\e085"; +} + +.oi-link-intact:before { + content:"\e086"; +} + +.oi-list-rich:before { + content:"\e087"; +} + +.oi-list:before { + content:"\e088"; +} + +.oi-location:before { + content:"\e089"; +} + +.oi-lock-locked:before { + content:"\e08a"; +} + +.oi-lock-unlocked:before { + content:"\e08b"; +} + +.oi-loop-circular:before { + content:"\e08c"; +} + +.oi-loop-square:before { + content:"\e08d"; +} + +.oi-loop:before { + content:"\e08e"; +} + +.oi-magnifying-glass:before { + content:"\e08f"; +} + +.oi-map-marker:before { + content:"\e090"; +} + +.oi-map:before { + content:"\e091"; +} + +.oi-media-pause:before { + content:"\e092"; +} + +.oi-media-play:before { + content:"\e093"; +} + +.oi-media-record:before { + content:"\e094"; +} + +.oi-media-skip-backward:before { + content:"\e095"; +} + +.oi-media-skip-forward:before { + content:"\e096"; +} + +.oi-media-step-backward:before { + content:"\e097"; +} + +.oi-media-step-forward:before { + content:"\e098"; +} + +.oi-media-stop:before { + content:"\e099"; +} + +.oi-medical-cross:before { + content:"\e09a"; +} + +.oi-menu:before { + content:"\e09b"; +} + +.oi-microphone:before { + content:"\e09c"; +} + +.oi-minus:before { + content:"\e09d"; +} + +.oi-monitor:before { + content:"\e09e"; +} + +.oi-moon:before { + content:"\e09f"; +} + +.oi-move:before { + content:"\e0a0"; +} + +.oi-musical-note:before { + content:"\e0a1"; +} + +.oi-paperclip:before { + content:"\e0a2"; +} + +.oi-pencil:before { + content:"\e0a3"; +} + +.oi-people:before { + content:"\e0a4"; +} + +.oi-person:before { + content:"\e0a5"; +} + +.oi-phone:before { + content:"\e0a6"; +} + +.oi-pie-chart:before { + content:"\e0a7"; +} + +.oi-pin:before { + content:"\e0a8"; +} + +.oi-play-circle:before { + content:"\e0a9"; +} + +.oi-plus:before { + content:"\e0aa"; +} + +.oi-power-standby:before { + content:"\e0ab"; +} + +.oi-print:before { + content:"\e0ac"; +} + +.oi-project:before { + content:"\e0ad"; +} + +.oi-pulse:before { + content:"\e0ae"; +} + +.oi-puzzle-piece:before { + content:"\e0af"; +} + +.oi-question-mark:before { + content:"\e0b0"; +} + +.oi-rain:before { + content:"\e0b1"; +} + +.oi-random:before { + content:"\e0b2"; +} + +.oi-reload:before { + content:"\e0b3"; +} + +.oi-resize-both:before { + content:"\e0b4"; +} + +.oi-resize-height:before { + content:"\e0b5"; +} + +.oi-resize-width:before { + content:"\e0b6"; +} + +.oi-rss-alt:before { + content:"\e0b7"; +} + +.oi-rss:before { + content:"\e0b8"; +} + +.oi-script:before { + content:"\e0b9"; +} + +.oi-share-boxed:before { + content:"\e0ba"; +} + +.oi-share:before { + content:"\e0bb"; +} + +.oi-shield:before { + content:"\e0bc"; +} + +.oi-signal:before { + content:"\e0bd"; +} + +.oi-signpost:before { + content:"\e0be"; +} + +.oi-sort-ascending:before { + content:"\e0bf"; +} + +.oi-sort-descending:before { + content:"\e0c0"; +} + +.oi-spreadsheet:before { + content:"\e0c1"; +} + +.oi-star:before { + content:"\e0c2"; +} + +.oi-sun:before { + content:"\e0c3"; +} + +.oi-tablet:before { + content:"\e0c4"; +} + +.oi-tag:before { + content:"\e0c5"; +} + +.oi-tags:before { + content:"\e0c6"; +} + +.oi-target:before { + content:"\e0c7"; +} + +.oi-task:before { + content:"\e0c8"; +} + +.oi-terminal:before { + content:"\e0c9"; +} + +.oi-text:before { + content:"\e0ca"; +} + +.oi-thumb-down:before { + content:"\e0cb"; +} + +.oi-thumb-up:before { + content:"\e0cc"; +} + +.oi-timer:before { + content:"\e0cd"; +} + +.oi-transfer:before { + content:"\e0ce"; +} + +.oi-trash:before { + content:"\e0cf"; +} + +.oi-underline:before { + content:"\e0d0"; +} + +.oi-vertical-align-bottom:before { + content:"\e0d1"; +} + +.oi-vertical-align-center:before { + content:"\e0d2"; +} + +.oi-vertical-align-top:before { + content:"\e0d3"; +} + +.oi-video:before { + content:"\e0d4"; +} + +.oi-volume-high:before { + content:"\e0d5"; +} + +.oi-volume-low:before { + content:"\e0d6"; +} + +.oi-volume-off:before { + content:"\e0d7"; +} + +.oi-warning:before { + content:"\e0d8"; +} + +.oi-wifi:before { + content:"\e0d9"; +} + +.oi-wrench:before { + content:"\e0da"; +} + +.oi-x:before { + content:"\e0db"; +} + +.oi-yen:before { + content:"\e0dc"; +} + +.oi-zoom-in:before { + content:"\e0dd"; +} + +.oi-zoom-out:before { + content:"\e0de"; +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.min.css b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.min.css new file mode 100644 index 00000000..4664f2e8 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.min.css @@ -0,0 +1 @@ +@font-face{font-family:Icons;src:url(../fonts/open-iconic.eot);src:url(../fonts/open-iconic.eot?#iconic-sm) format('embedded-opentype'),url(../fonts/open-iconic.woff) format('woff'),url(../fonts/open-iconic.ttf) format('truetype'),url(../fonts/open-iconic.otf) format('opentype'),url(../fonts/open-iconic.svg#iconic-sm) format('svg');font-weight:400;font-style:normal}.oi{position:relative;top:1px;display:inline-block;speak:none;font-family:Icons;font-style:normal;font-weight:400;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.oi:empty:before{width:1em;text-align:center;box-sizing:content-box}.oi.oi-align-center:before{text-align:center}.oi.oi-align-left:before{text-align:left}.oi.oi-align-right:before{text-align:right}.oi.oi-flip-horizontal:before{-webkit-transform:scale(-1,1);-ms-transform:scale(-1,1);transform:scale(-1,1)}.oi.oi-flip-vertical:before{-webkit-transform:scale(1,-1);-ms-transform:scale(-1,1);transform:scale(1,-1)}.oi.oi-flip-horizontal-vertical:before{-webkit-transform:scale(-1,-1);-ms-transform:scale(-1,1);transform:scale(-1,-1)}.oi-account-login:before{content:'\e000'}.oi-account-logout:before{content:'\e001'}.oi-action-redo:before{content:'\e002'}.oi-action-undo:before{content:'\e003'}.oi-align-center:before{content:'\e004'}.oi-align-left:before{content:'\e005'}.oi-align-right:before{content:'\e006'}.oi-aperture:before{content:'\e007'}.oi-arrow-bottom:before{content:'\e008'}.oi-arrow-circle-bottom:before{content:'\e009'}.oi-arrow-circle-left:before{content:'\e00a'}.oi-arrow-circle-right:before{content:'\e00b'}.oi-arrow-circle-top:before{content:'\e00c'}.oi-arrow-left:before{content:'\e00d'}.oi-arrow-right:before{content:'\e00e'}.oi-arrow-thick-bottom:before{content:'\e00f'}.oi-arrow-thick-left:before{content:'\e010'}.oi-arrow-thick-right:before{content:'\e011'}.oi-arrow-thick-top:before{content:'\e012'}.oi-arrow-top:before{content:'\e013'}.oi-audio-spectrum:before{content:'\e014'}.oi-audio:before{content:'\e015'}.oi-badge:before{content:'\e016'}.oi-ban:before{content:'\e017'}.oi-bar-chart:before{content:'\e018'}.oi-basket:before{content:'\e019'}.oi-battery-empty:before{content:'\e01a'}.oi-battery-full:before{content:'\e01b'}.oi-beaker:before{content:'\e01c'}.oi-bell:before{content:'\e01d'}.oi-bluetooth:before{content:'\e01e'}.oi-bold:before{content:'\e01f'}.oi-bolt:before{content:'\e020'}.oi-book:before{content:'\e021'}.oi-bookmark:before{content:'\e022'}.oi-box:before{content:'\e023'}.oi-briefcase:before{content:'\e024'}.oi-british-pound:before{content:'\e025'}.oi-browser:before{content:'\e026'}.oi-brush:before{content:'\e027'}.oi-bug:before{content:'\e028'}.oi-bullhorn:before{content:'\e029'}.oi-calculator:before{content:'\e02a'}.oi-calendar:before{content:'\e02b'}.oi-camera-slr:before{content:'\e02c'}.oi-caret-bottom:before{content:'\e02d'}.oi-caret-left:before{content:'\e02e'}.oi-caret-right:before{content:'\e02f'}.oi-caret-top:before{content:'\e030'}.oi-cart:before{content:'\e031'}.oi-chat:before{content:'\e032'}.oi-check:before{content:'\e033'}.oi-chevron-bottom:before{content:'\e034'}.oi-chevron-left:before{content:'\e035'}.oi-chevron-right:before{content:'\e036'}.oi-chevron-top:before{content:'\e037'}.oi-circle-check:before{content:'\e038'}.oi-circle-x:before{content:'\e039'}.oi-clipboard:before{content:'\e03a'}.oi-clock:before{content:'\e03b'}.oi-cloud-download:before{content:'\e03c'}.oi-cloud-upload:before{content:'\e03d'}.oi-cloud:before{content:'\e03e'}.oi-cloudy:before{content:'\e03f'}.oi-code:before{content:'\e040'}.oi-cog:before{content:'\e041'}.oi-collapse-down:before{content:'\e042'}.oi-collapse-left:before{content:'\e043'}.oi-collapse-right:before{content:'\e044'}.oi-collapse-up:before{content:'\e045'}.oi-command:before{content:'\e046'}.oi-comment-square:before{content:'\e047'}.oi-compass:before{content:'\e048'}.oi-contrast:before{content:'\e049'}.oi-copywriting:before{content:'\e04a'}.oi-credit-card:before{content:'\e04b'}.oi-crop:before{content:'\e04c'}.oi-dashboard:before{content:'\e04d'}.oi-data-transfer-download:before{content:'\e04e'}.oi-data-transfer-upload:before{content:'\e04f'}.oi-delete:before{content:'\e050'}.oi-dial:before{content:'\e051'}.oi-document:before{content:'\e052'}.oi-dollar:before{content:'\e053'}.oi-double-quote-sans-left:before{content:'\e054'}.oi-double-quote-sans-right:before{content:'\e055'}.oi-double-quote-serif-left:before{content:'\e056'}.oi-double-quote-serif-right:before{content:'\e057'}.oi-droplet:before{content:'\e058'}.oi-eject:before{content:'\e059'}.oi-elevator:before{content:'\e05a'}.oi-ellipses:before{content:'\e05b'}.oi-envelope-closed:before{content:'\e05c'}.oi-envelope-open:before{content:'\e05d'}.oi-euro:before{content:'\e05e'}.oi-excerpt:before{content:'\e05f'}.oi-expand-down:before{content:'\e060'}.oi-expand-left:before{content:'\e061'}.oi-expand-right:before{content:'\e062'}.oi-expand-up:before{content:'\e063'}.oi-external-link:before{content:'\e064'}.oi-eye:before{content:'\e065'}.oi-eyedropper:before{content:'\e066'}.oi-file:before{content:'\e067'}.oi-fire:before{content:'\e068'}.oi-flag:before{content:'\e069'}.oi-flash:before{content:'\e06a'}.oi-folder:before{content:'\e06b'}.oi-fork:before{content:'\e06c'}.oi-fullscreen-enter:before{content:'\e06d'}.oi-fullscreen-exit:before{content:'\e06e'}.oi-globe:before{content:'\e06f'}.oi-graph:before{content:'\e070'}.oi-grid-four-up:before{content:'\e071'}.oi-grid-three-up:before{content:'\e072'}.oi-grid-two-up:before{content:'\e073'}.oi-hard-drive:before{content:'\e074'}.oi-header:before{content:'\e075'}.oi-headphones:before{content:'\e076'}.oi-heart:before{content:'\e077'}.oi-home:before{content:'\e078'}.oi-image:before{content:'\e079'}.oi-inbox:before{content:'\e07a'}.oi-infinity:before{content:'\e07b'}.oi-info:before{content:'\e07c'}.oi-italic:before{content:'\e07d'}.oi-justify-center:before{content:'\e07e'}.oi-justify-left:before{content:'\e07f'}.oi-justify-right:before{content:'\e080'}.oi-key:before{content:'\e081'}.oi-laptop:before{content:'\e082'}.oi-layers:before{content:'\e083'}.oi-lightbulb:before{content:'\e084'}.oi-link-broken:before{content:'\e085'}.oi-link-intact:before{content:'\e086'}.oi-list-rich:before{content:'\e087'}.oi-list:before{content:'\e088'}.oi-location:before{content:'\e089'}.oi-lock-locked:before{content:'\e08a'}.oi-lock-unlocked:before{content:'\e08b'}.oi-loop-circular:before{content:'\e08c'}.oi-loop-square:before{content:'\e08d'}.oi-loop:before{content:'\e08e'}.oi-magnifying-glass:before{content:'\e08f'}.oi-map-marker:before{content:'\e090'}.oi-map:before{content:'\e091'}.oi-media-pause:before{content:'\e092'}.oi-media-play:before{content:'\e093'}.oi-media-record:before{content:'\e094'}.oi-media-skip-backward:before{content:'\e095'}.oi-media-skip-forward:before{content:'\e096'}.oi-media-step-backward:before{content:'\e097'}.oi-media-step-forward:before{content:'\e098'}.oi-media-stop:before{content:'\e099'}.oi-medical-cross:before{content:'\e09a'}.oi-menu:before{content:'\e09b'}.oi-microphone:before{content:'\e09c'}.oi-minus:before{content:'\e09d'}.oi-monitor:before{content:'\e09e'}.oi-moon:before{content:'\e09f'}.oi-move:before{content:'\e0a0'}.oi-musical-note:before{content:'\e0a1'}.oi-paperclip:before{content:'\e0a2'}.oi-pencil:before{content:'\e0a3'}.oi-people:before{content:'\e0a4'}.oi-person:before{content:'\e0a5'}.oi-phone:before{content:'\e0a6'}.oi-pie-chart:before{content:'\e0a7'}.oi-pin:before{content:'\e0a8'}.oi-play-circle:before{content:'\e0a9'}.oi-plus:before{content:'\e0aa'}.oi-power-standby:before{content:'\e0ab'}.oi-print:before{content:'\e0ac'}.oi-project:before{content:'\e0ad'}.oi-pulse:before{content:'\e0ae'}.oi-puzzle-piece:before{content:'\e0af'}.oi-question-mark:before{content:'\e0b0'}.oi-rain:before{content:'\e0b1'}.oi-random:before{content:'\e0b2'}.oi-reload:before{content:'\e0b3'}.oi-resize-both:before{content:'\e0b4'}.oi-resize-height:before{content:'\e0b5'}.oi-resize-width:before{content:'\e0b6'}.oi-rss-alt:before{content:'\e0b7'}.oi-rss:before{content:'\e0b8'}.oi-script:before{content:'\e0b9'}.oi-share-boxed:before{content:'\e0ba'}.oi-share:before{content:'\e0bb'}.oi-shield:before{content:'\e0bc'}.oi-signal:before{content:'\e0bd'}.oi-signpost:before{content:'\e0be'}.oi-sort-ascending:before{content:'\e0bf'}.oi-sort-descending:before{content:'\e0c0'}.oi-spreadsheet:before{content:'\e0c1'}.oi-star:before{content:'\e0c2'}.oi-sun:before{content:'\e0c3'}.oi-tablet:before{content:'\e0c4'}.oi-tag:before{content:'\e0c5'}.oi-tags:before{content:'\e0c6'}.oi-target:before{content:'\e0c7'}.oi-task:before{content:'\e0c8'}.oi-terminal:before{content:'\e0c9'}.oi-text:before{content:'\e0ca'}.oi-thumb-down:before{content:'\e0cb'}.oi-thumb-up:before{content:'\e0cc'}.oi-timer:before{content:'\e0cd'}.oi-transfer:before{content:'\e0ce'}.oi-trash:before{content:'\e0cf'}.oi-underline:before{content:'\e0d0'}.oi-vertical-align-bottom:before{content:'\e0d1'}.oi-vertical-align-center:before{content:'\e0d2'}.oi-vertical-align-top:before{content:'\e0d3'}.oi-video:before{content:'\e0d4'}.oi-volume-high:before{content:'\e0d5'}.oi-volume-low:before{content:'\e0d6'}.oi-volume-off:before{content:'\e0d7'}.oi-warning:before{content:'\e0d8'}.oi-wifi:before{content:'\e0d9'}.oi-wrench:before{content:'\e0da'}.oi-x:before{content:'\e0db'}.oi-yen:before{content:'\e0dc'}.oi-zoom-in:before{content:'\e0dd'}.oi-zoom-out:before{content:'\e0de'} \ No newline at end of file diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.scss b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.scss new file mode 100644 index 00000000..18f01e26 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.scss @@ -0,0 +1,958 @@ +/* Bootstrap */ + +/* Override Bootstrap default variable */ +$icon-font-path: '../fonts/' !default; + +@font-face { + font-family: 'Icons'; + src: url('#{$icon-font-path}open-iconic.eot'); + src: url('#{$icon-font-path}open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('#{$icon-font-path}open-iconic.woff') format('woff'), url('#{$icon-font-path}open-iconic.ttf') format('truetype'), url('#{$icon-font-path}open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + +// Catchall baseclass +.oi { + position: relative; + top: 1px; + display: inline-block; + font-family: 'Icons'; + font-style: normal; + font-weight: normal; + line-height: 1; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + + + &:empty:before { + width: 1em; + text-align: center; + box-sizing: content-box; + } + + &.oi-align-center:before { + text-align: center; + } + + &.oi-align-left:before { + text-align: left; + } + + &.oi-align-right:before { + text-align: right; + } + + + &.oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); + } + + &.oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); + } + + &.oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); + } +} + + + +.oi-account-login:before { + content:'\e000'; +} + +.oi-account-logout:before { + content:'\e001'; +} + +.oi-action-redo:before { + content:'\e002'; +} + +.oi-action-undo:before { + content:'\e003'; +} + +.oi-align-center:before { + content:'\e004'; +} + +.oi-align-left:before { + content:'\e005'; +} + +.oi-align-right:before { + content:'\e006'; +} + +.oi-aperture:before { + content:'\e007'; +} + +.oi-arrow-bottom:before { + content:'\e008'; +} + +.oi-arrow-circle-bottom:before { + content:'\e009'; +} + +.oi-arrow-circle-left:before { + content:'\e00a'; +} + +.oi-arrow-circle-right:before { + content:'\e00b'; +} + +.oi-arrow-circle-top:before { + content:'\e00c'; +} + +.oi-arrow-left:before { + content:'\e00d'; +} + +.oi-arrow-right:before { + content:'\e00e'; +} + +.oi-arrow-thick-bottom:before { + content:'\e00f'; +} + +.oi-arrow-thick-left:before { + content:'\e010'; +} + +.oi-arrow-thick-right:before { + content:'\e011'; +} + +.oi-arrow-thick-top:before { + content:'\e012'; +} + +.oi-arrow-top:before { + content:'\e013'; +} + +.oi-audio-spectrum:before { + content:'\e014'; +} + +.oi-audio:before { + content:'\e015'; +} + +.oi-badge:before { + content:'\e016'; +} + +.oi-ban:before { + content:'\e017'; +} + +.oi-bar-chart:before { + content:'\e018'; +} + +.oi-basket:before { + content:'\e019'; +} + +.oi-battery-empty:before { + content:'\e01a'; +} + +.oi-battery-full:before { + content:'\e01b'; +} + +.oi-beaker:before { + content:'\e01c'; +} + +.oi-bell:before { + content:'\e01d'; +} + +.oi-bluetooth:before { + content:'\e01e'; +} + +.oi-bold:before { + content:'\e01f'; +} + +.oi-bolt:before { + content:'\e020'; +} + +.oi-book:before { + content:'\e021'; +} + +.oi-bookmark:before { + content:'\e022'; +} + +.oi-box:before { + content:'\e023'; +} + +.oi-briefcase:before { + content:'\e024'; +} + +.oi-british-pound:before { + content:'\e025'; +} + +.oi-browser:before { + content:'\e026'; +} + +.oi-brush:before { + content:'\e027'; +} + +.oi-bug:before { + content:'\e028'; +} + +.oi-bullhorn:before { + content:'\e029'; +} + +.oi-calculator:before { + content:'\e02a'; +} + +.oi-calendar:before { + content:'\e02b'; +} + +.oi-camera-slr:before { + content:'\e02c'; +} + +.oi-caret-bottom:before { + content:'\e02d'; +} + +.oi-caret-left:before { + content:'\e02e'; +} + +.oi-caret-right:before { + content:'\e02f'; +} + +.oi-caret-top:before { + content:'\e030'; +} + +.oi-cart:before { + content:'\e031'; +} + +.oi-chat:before { + content:'\e032'; +} + +.oi-check:before { + content:'\e033'; +} + +.oi-chevron-bottom:before { + content:'\e034'; +} + +.oi-chevron-left:before { + content:'\e035'; +} + +.oi-chevron-right:before { + content:'\e036'; +} + +.oi-chevron-top:before { + content:'\e037'; +} + +.oi-circle-check:before { + content:'\e038'; +} + +.oi-circle-x:before { + content:'\e039'; +} + +.oi-clipboard:before { + content:'\e03a'; +} + +.oi-clock:before { + content:'\e03b'; +} + +.oi-cloud-download:before { + content:'\e03c'; +} + +.oi-cloud-upload:before { + content:'\e03d'; +} + +.oi-cloud:before { + content:'\e03e'; +} + +.oi-cloudy:before { + content:'\e03f'; +} + +.oi-code:before { + content:'\e040'; +} + +.oi-cog:before { + content:'\e041'; +} + +.oi-collapse-down:before { + content:'\e042'; +} + +.oi-collapse-left:before { + content:'\e043'; +} + +.oi-collapse-right:before { + content:'\e044'; +} + +.oi-collapse-up:before { + content:'\e045'; +} + +.oi-command:before { + content:'\e046'; +} + +.oi-comment-square:before { + content:'\e047'; +} + +.oi-compass:before { + content:'\e048'; +} + +.oi-contrast:before { + content:'\e049'; +} + +.oi-copywriting:before { + content:'\e04a'; +} + +.oi-credit-card:before { + content:'\e04b'; +} + +.oi-crop:before { + content:'\e04c'; +} + +.oi-dashboard:before { + content:'\e04d'; +} + +.oi-data-transfer-download:before { + content:'\e04e'; +} + +.oi-data-transfer-upload:before { + content:'\e04f'; +} + +.oi-delete:before { + content:'\e050'; +} + +.oi-dial:before { + content:'\e051'; +} + +.oi-document:before { + content:'\e052'; +} + +.oi-dollar:before { + content:'\e053'; +} + +.oi-double-quote-sans-left:before { + content:'\e054'; +} + +.oi-double-quote-sans-right:before { + content:'\e055'; +} + +.oi-double-quote-serif-left:before { + content:'\e056'; +} + +.oi-double-quote-serif-right:before { + content:'\e057'; +} + +.oi-droplet:before { + content:'\e058'; +} + +.oi-eject:before { + content:'\e059'; +} + +.oi-elevator:before { + content:'\e05a'; +} + +.oi-ellipses:before { + content:'\e05b'; +} + +.oi-envelope-closed:before { + content:'\e05c'; +} + +.oi-envelope-open:before { + content:'\e05d'; +} + +.oi-euro:before { + content:'\e05e'; +} + +.oi-excerpt:before { + content:'\e05f'; +} + +.oi-expand-down:before { + content:'\e060'; +} + +.oi-expand-left:before { + content:'\e061'; +} + +.oi-expand-right:before { + content:'\e062'; +} + +.oi-expand-up:before { + content:'\e063'; +} + +.oi-external-link:before { + content:'\e064'; +} + +.oi-eye:before { + content:'\e065'; +} + +.oi-eyedropper:before { + content:'\e066'; +} + +.oi-file:before { + content:'\e067'; +} + +.oi-fire:before { + content:'\e068'; +} + +.oi-flag:before { + content:'\e069'; +} + +.oi-flash:before { + content:'\e06a'; +} + +.oi-folder:before { + content:'\e06b'; +} + +.oi-fork:before { + content:'\e06c'; +} + +.oi-fullscreen-enter:before { + content:'\e06d'; +} + +.oi-fullscreen-exit:before { + content:'\e06e'; +} + +.oi-globe:before { + content:'\e06f'; +} + +.oi-graph:before { + content:'\e070'; +} + +.oi-grid-four-up:before { + content:'\e071'; +} + +.oi-grid-three-up:before { + content:'\e072'; +} + +.oi-grid-two-up:before { + content:'\e073'; +} + +.oi-hard-drive:before { + content:'\e074'; +} + +.oi-header:before { + content:'\e075'; +} + +.oi-headphones:before { + content:'\e076'; +} + +.oi-heart:before { + content:'\e077'; +} + +.oi-home:before { + content:'\e078'; +} + +.oi-image:before { + content:'\e079'; +} + +.oi-inbox:before { + content:'\e07a'; +} + +.oi-infinity:before { + content:'\e07b'; +} + +.oi-info:before { + content:'\e07c'; +} + +.oi-italic:before { + content:'\e07d'; +} + +.oi-justify-center:before { + content:'\e07e'; +} + +.oi-justify-left:before { + content:'\e07f'; +} + +.oi-justify-right:before { + content:'\e080'; +} + +.oi-key:before { + content:'\e081'; +} + +.oi-laptop:before { + content:'\e082'; +} + +.oi-layers:before { + content:'\e083'; +} + +.oi-lightbulb:before { + content:'\e084'; +} + +.oi-link-broken:before { + content:'\e085'; +} + +.oi-link-intact:before { + content:'\e086'; +} + +.oi-list-rich:before { + content:'\e087'; +} + +.oi-list:before { + content:'\e088'; +} + +.oi-location:before { + content:'\e089'; +} + +.oi-lock-locked:before { + content:'\e08a'; +} + +.oi-lock-unlocked:before { + content:'\e08b'; +} + +.oi-loop-circular:before { + content:'\e08c'; +} + +.oi-loop-square:before { + content:'\e08d'; +} + +.oi-loop:before { + content:'\e08e'; +} + +.oi-magnifying-glass:before { + content:'\e08f'; +} + +.oi-map-marker:before { + content:'\e090'; +} + +.oi-map:before { + content:'\e091'; +} + +.oi-media-pause:before { + content:'\e092'; +} + +.oi-media-play:before { + content:'\e093'; +} + +.oi-media-record:before { + content:'\e094'; +} + +.oi-media-skip-backward:before { + content:'\e095'; +} + +.oi-media-skip-forward:before { + content:'\e096'; +} + +.oi-media-step-backward:before { + content:'\e097'; +} + +.oi-media-step-forward:before { + content:'\e098'; +} + +.oi-media-stop:before { + content:'\e099'; +} + +.oi-medical-cross:before { + content:'\e09a'; +} + +.oi-menu:before { + content:'\e09b'; +} + +.oi-microphone:before { + content:'\e09c'; +} + +.oi-minus:before { + content:'\e09d'; +} + +.oi-monitor:before { + content:'\e09e'; +} + +.oi-moon:before { + content:'\e09f'; +} + +.oi-move:before { + content:'\e0a0'; +} + +.oi-musical-note:before { + content:'\e0a1'; +} + +.oi-paperclip:before { + content:'\e0a2'; +} + +.oi-pencil:before { + content:'\e0a3'; +} + +.oi-people:before { + content:'\e0a4'; +} + +.oi-person:before { + content:'\e0a5'; +} + +.oi-phone:before { + content:'\e0a6'; +} + +.oi-pie-chart:before { + content:'\e0a7'; +} + +.oi-pin:before { + content:'\e0a8'; +} + +.oi-play-circle:before { + content:'\e0a9'; +} + +.oi-plus:before { + content:'\e0aa'; +} + +.oi-power-standby:before { + content:'\e0ab'; +} + +.oi-print:before { + content:'\e0ac'; +} + +.oi-project:before { + content:'\e0ad'; +} + +.oi-pulse:before { + content:'\e0ae'; +} + +.oi-puzzle-piece:before { + content:'\e0af'; +} + +.oi-question-mark:before { + content:'\e0b0'; +} + +.oi-rain:before { + content:'\e0b1'; +} + +.oi-random:before { + content:'\e0b2'; +} + +.oi-reload:before { + content:'\e0b3'; +} + +.oi-resize-both:before { + content:'\e0b4'; +} + +.oi-resize-height:before { + content:'\e0b5'; +} + +.oi-resize-width:before { + content:'\e0b6'; +} + +.oi-rss-alt:before { + content:'\e0b7'; +} + +.oi-rss:before { + content:'\e0b8'; +} + +.oi-script:before { + content:'\e0b9'; +} + +.oi-share-boxed:before { + content:'\e0ba'; +} + +.oi-share:before { + content:'\e0bb'; +} + +.oi-shield:before { + content:'\e0bc'; +} + +.oi-signal:before { + content:'\e0bd'; +} + +.oi-signpost:before { + content:'\e0be'; +} + +.oi-sort-ascending:before { + content:'\e0bf'; +} + +.oi-sort-descending:before { + content:'\e0c0'; +} + +.oi-spreadsheet:before { + content:'\e0c1'; +} + +.oi-star:before { + content:'\e0c2'; +} + +.oi-sun:before { + content:'\e0c3'; +} + +.oi-tablet:before { + content:'\e0c4'; +} + +.oi-tag:before { + content:'\e0c5'; +} + +.oi-tags:before { + content:'\e0c6'; +} + +.oi-target:before { + content:'\e0c7'; +} + +.oi-task:before { + content:'\e0c8'; +} + +.oi-terminal:before { + content:'\e0c9'; +} + +.oi-text:before { + content:'\e0ca'; +} + +.oi-thumb-down:before { + content:'\e0cb'; +} + +.oi-thumb-up:before { + content:'\e0cc'; +} + +.oi-timer:before { + content:'\e0cd'; +} + +.oi-transfer:before { + content:'\e0ce'; +} + +.oi-trash:before { + content:'\e0cf'; +} + +.oi-underline:before { + content:'\e0d0'; +} + +.oi-vertical-align-bottom:before { + content:'\e0d1'; +} + +.oi-vertical-align-center:before { + content:'\e0d2'; +} + +.oi-vertical-align-top:before { + content:'\e0d3'; +} + +.oi-video:before { + content:'\e0d4'; +} + +.oi-volume-high:before { + content:'\e0d5'; +} + +.oi-volume-low:before { + content:'\e0d6'; +} + +.oi-volume-off:before { + content:'\e0d7'; +} + +.oi-warning:before { + content:'\e0d8'; +} + +.oi-wifi:before { + content:'\e0d9'; +} + +.oi-wrench:before { + content:'\e0da'; +} + +.oi-x:before { + content:'\e0db'; +} + +.oi-yen:before { + content:'\e0dc'; +} + +.oi-zoom-in:before { + content:'\e0dd'; +} + +.oi-zoom-out:before { + content:'\e0de'; +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.styl b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.styl new file mode 100644 index 00000000..0afa2548 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-bootstrap.styl @@ -0,0 +1,954 @@ +/* Bootstrap */ + +@font-face + font-family 'Icons' + src url('../fonts/open-iconic.eot') + src url('../fonts/open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('../fonts/open-iconic.woff') format('woff'), url('../fonts/open-iconic.ttf') format('truetype'), url('../fonts/open-iconic.svg#iconic-sm') format('svg') + font-weight normal + font-style normal + + +// Catchall baseclass +.oi + position relative + top 1px + display inline-block + font-family 'Icons' + font-style normal + font-weight normal + line-height 1 + -webkit-font-smoothing antialiased + -moz-osx-font-smoothing grayscale + + + &:empty:before + width 1em + text-align center + box-sizing content-box + + &.oi-align-center:before + text-align center + + + &.oi-align-left:before + text-align left + + + &.oi-align-right:before + text-align right + + + + &.oi-flip-horizontal:before + -webkit-transform scale(-1, 1) + -ms-transform scale(-1, 1) + transform scale(-1, 1) + + + &.oi-flip-vertical:before + -webkit-transform scale(1, -1) + -ms-transform scale(-1, 1) + transform scale(1, -1) + + + &.oi-flip-horizontal-vertical:before + -webkit-transform scale(-1, -1) + -ms-transform scale(-1, 1) + transform scale(-1, -1) + + + + + +.oi-account-login:before { + content'\e000' +} + +.oi-account-logout:before { + content'\e001' +} + +.oi-action-redo:before { + content'\e002' +} + +.oi-action-undo:before { + content'\e003' +} + +.oi-align-center:before { + content'\e004' +} + +.oi-align-left:before { + content'\e005' +} + +.oi-align-right:before { + content'\e006' +} + +.oi-aperture:before { + content'\e007' +} + +.oi-arrow-bottom:before { + content'\e008' +} + +.oi-arrow-circle-bottom:before { + content'\e009' +} + +.oi-arrow-circle-left:before { + content'\e00a' +} + +.oi-arrow-circle-right:before { + content'\e00b' +} + +.oi-arrow-circle-top:before { + content'\e00c' +} + +.oi-arrow-left:before { + content'\e00d' +} + +.oi-arrow-right:before { + content'\e00e' +} + +.oi-arrow-thick-bottom:before { + content'\e00f' +} + +.oi-arrow-thick-left:before { + content'\e010' +} + +.oi-arrow-thick-right:before { + content'\e011' +} + +.oi-arrow-thick-top:before { + content'\e012' +} + +.oi-arrow-top:before { + content'\e013' +} + +.oi-audio-spectrum:before { + content'\e014' +} + +.oi-audio:before { + content'\e015' +} + +.oi-badge:before { + content'\e016' +} + +.oi-ban:before { + content'\e017' +} + +.oi-bar-chart:before { + content'\e018' +} + +.oi-basket:before { + content'\e019' +} + +.oi-battery-empty:before { + content'\e01a' +} + +.oi-battery-full:before { + content'\e01b' +} + +.oi-beaker:before { + content'\e01c' +} + +.oi-bell:before { + content'\e01d' +} + +.oi-bluetooth:before { + content'\e01e' +} + +.oi-bold:before { + content'\e01f' +} + +.oi-bolt:before { + content'\e020' +} + +.oi-book:before { + content'\e021' +} + +.oi-bookmark:before { + content'\e022' +} + +.oi-box:before { + content'\e023' +} + +.oi-briefcase:before { + content'\e024' +} + +.oi-british-pound:before { + content'\e025' +} + +.oi-browser:before { + content'\e026' +} + +.oi-brush:before { + content'\e027' +} + +.oi-bug:before { + content'\e028' +} + +.oi-bullhorn:before { + content'\e029' +} + +.oi-calculator:before { + content'\e02a' +} + +.oi-calendar:before { + content'\e02b' +} + +.oi-camera-slr:before { + content'\e02c' +} + +.oi-caret-bottom:before { + content'\e02d' +} + +.oi-caret-left:before { + content'\e02e' +} + +.oi-caret-right:before { + content'\e02f' +} + +.oi-caret-top:before { + content'\e030' +} + +.oi-cart:before { + content'\e031' +} + +.oi-chat:before { + content'\e032' +} + +.oi-check:before { + content'\e033' +} + +.oi-chevron-bottom:before { + content'\e034' +} + +.oi-chevron-left:before { + content'\e035' +} + +.oi-chevron-right:before { + content'\e036' +} + +.oi-chevron-top:before { + content'\e037' +} + +.oi-circle-check:before { + content'\e038' +} + +.oi-circle-x:before { + content'\e039' +} + +.oi-clipboard:before { + content'\e03a' +} + +.oi-clock:before { + content'\e03b' +} + +.oi-cloud-download:before { + content'\e03c' +} + +.oi-cloud-upload:before { + content'\e03d' +} + +.oi-cloud:before { + content'\e03e' +} + +.oi-cloudy:before { + content'\e03f' +} + +.oi-code:before { + content'\e040' +} + +.oi-cog:before { + content'\e041' +} + +.oi-collapse-down:before { + content'\e042' +} + +.oi-collapse-left:before { + content'\e043' +} + +.oi-collapse-right:before { + content'\e044' +} + +.oi-collapse-up:before { + content'\e045' +} + +.oi-command:before { + content'\e046' +} + +.oi-comment-square:before { + content'\e047' +} + +.oi-compass:before { + content'\e048' +} + +.oi-contrast:before { + content'\e049' +} + +.oi-copywriting:before { + content'\e04a' +} + +.oi-credit-card:before { + content'\e04b' +} + +.oi-crop:before { + content'\e04c' +} + +.oi-dashboard:before { + content'\e04d' +} + +.oi-data-transfer-download:before { + content'\e04e' +} + +.oi-data-transfer-upload:before { + content'\e04f' +} + +.oi-delete:before { + content'\e050' +} + +.oi-dial:before { + content'\e051' +} + +.oi-document:before { + content'\e052' +} + +.oi-dollar:before { + content'\e053' +} + +.oi-double-quote-sans-left:before { + content'\e054' +} + +.oi-double-quote-sans-right:before { + content'\e055' +} + +.oi-double-quote-serif-left:before { + content'\e056' +} + +.oi-double-quote-serif-right:before { + content'\e057' +} + +.oi-droplet:before { + content'\e058' +} + +.oi-eject:before { + content'\e059' +} + +.oi-elevator:before { + content'\e05a' +} + +.oi-ellipses:before { + content'\e05b' +} + +.oi-envelope-closed:before { + content'\e05c' +} + +.oi-envelope-open:before { + content'\e05d' +} + +.oi-euro:before { + content'\e05e' +} + +.oi-excerpt:before { + content'\e05f' +} + +.oi-expand-down:before { + content'\e060' +} + +.oi-expand-left:before { + content'\e061' +} + +.oi-expand-right:before { + content'\e062' +} + +.oi-expand-up:before { + content'\e063' +} + +.oi-external-link:before { + content'\e064' +} + +.oi-eye:before { + content'\e065' +} + +.oi-eyedropper:before { + content'\e066' +} + +.oi-file:before { + content'\e067' +} + +.oi-fire:before { + content'\e068' +} + +.oi-flag:before { + content'\e069' +} + +.oi-flash:before { + content'\e06a' +} + +.oi-folder:before { + content'\e06b' +} + +.oi-fork:before { + content'\e06c' +} + +.oi-fullscreen-enter:before { + content'\e06d' +} + +.oi-fullscreen-exit:before { + content'\e06e' +} + +.oi-globe:before { + content'\e06f' +} + +.oi-graph:before { + content'\e070' +} + +.oi-grid-four-up:before { + content'\e071' +} + +.oi-grid-three-up:before { + content'\e072' +} + +.oi-grid-two-up:before { + content'\e073' +} + +.oi-hard-drive:before { + content'\e074' +} + +.oi-header:before { + content'\e075' +} + +.oi-headphones:before { + content'\e076' +} + +.oi-heart:before { + content'\e077' +} + +.oi-home:before { + content'\e078' +} + +.oi-image:before { + content'\e079' +} + +.oi-inbox:before { + content'\e07a' +} + +.oi-infinity:before { + content'\e07b' +} + +.oi-info:before { + content'\e07c' +} + +.oi-italic:before { + content'\e07d' +} + +.oi-justify-center:before { + content'\e07e' +} + +.oi-justify-left:before { + content'\e07f' +} + +.oi-justify-right:before { + content'\e080' +} + +.oi-key:before { + content'\e081' +} + +.oi-laptop:before { + content'\e082' +} + +.oi-layers:before { + content'\e083' +} + +.oi-lightbulb:before { + content'\e084' +} + +.oi-link-broken:before { + content'\e085' +} + +.oi-link-intact:before { + content'\e086' +} + +.oi-list-rich:before { + content'\e087' +} + +.oi-list:before { + content'\e088' +} + +.oi-location:before { + content'\e089' +} + +.oi-lock-locked:before { + content'\e08a' +} + +.oi-lock-unlocked:before { + content'\e08b' +} + +.oi-loop-circular:before { + content'\e08c' +} + +.oi-loop-square:before { + content'\e08d' +} + +.oi-loop:before { + content'\e08e' +} + +.oi-magnifying-glass:before { + content'\e08f' +} + +.oi-map-marker:before { + content'\e090' +} + +.oi-map:before { + content'\e091' +} + +.oi-media-pause:before { + content'\e092' +} + +.oi-media-play:before { + content'\e093' +} + +.oi-media-record:before { + content'\e094' +} + +.oi-media-skip-backward:before { + content'\e095' +} + +.oi-media-skip-forward:before { + content'\e096' +} + +.oi-media-step-backward:before { + content'\e097' +} + +.oi-media-step-forward:before { + content'\e098' +} + +.oi-media-stop:before { + content'\e099' +} + +.oi-medical-cross:before { + content'\e09a' +} + +.oi-menu:before { + content'\e09b' +} + +.oi-microphone:before { + content'\e09c' +} + +.oi-minus:before { + content'\e09d' +} + +.oi-monitor:before { + content'\e09e' +} + +.oi-moon:before { + content'\e09f' +} + +.oi-move:before { + content'\e0a0' +} + +.oi-musical-note:before { + content'\e0a1' +} + +.oi-paperclip:before { + content'\e0a2' +} + +.oi-pencil:before { + content'\e0a3' +} + +.oi-people:before { + content'\e0a4' +} + +.oi-person:before { + content'\e0a5' +} + +.oi-phone:before { + content'\e0a6' +} + +.oi-pie-chart:before { + content'\e0a7' +} + +.oi-pin:before { + content'\e0a8' +} + +.oi-play-circle:before { + content'\e0a9' +} + +.oi-plus:before { + content'\e0aa' +} + +.oi-power-standby:before { + content'\e0ab' +} + +.oi-print:before { + content'\e0ac' +} + +.oi-project:before { + content'\e0ad' +} + +.oi-pulse:before { + content'\e0ae' +} + +.oi-puzzle-piece:before { + content'\e0af' +} + +.oi-question-mark:before { + content'\e0b0' +} + +.oi-rain:before { + content'\e0b1' +} + +.oi-random:before { + content'\e0b2' +} + +.oi-reload:before { + content'\e0b3' +} + +.oi-resize-both:before { + content'\e0b4' +} + +.oi-resize-height:before { + content'\e0b5' +} + +.oi-resize-width:before { + content'\e0b6' +} + +.oi-rss-alt:before { + content'\e0b7' +} + +.oi-rss:before { + content'\e0b8' +} + +.oi-script:before { + content'\e0b9' +} + +.oi-share-boxed:before { + content'\e0ba' +} + +.oi-share:before { + content'\e0bb' +} + +.oi-shield:before { + content'\e0bc' +} + +.oi-signal:before { + content'\e0bd' +} + +.oi-signpost:before { + content'\e0be' +} + +.oi-sort-ascending:before { + content'\e0bf' +} + +.oi-sort-descending:before { + content'\e0c0' +} + +.oi-spreadsheet:before { + content'\e0c1' +} + +.oi-star:before { + content'\e0c2' +} + +.oi-sun:before { + content'\e0c3' +} + +.oi-tablet:before { + content'\e0c4' +} + +.oi-tag:before { + content'\e0c5' +} + +.oi-tags:before { + content'\e0c6' +} + +.oi-target:before { + content'\e0c7' +} + +.oi-task:before { + content'\e0c8' +} + +.oi-terminal:before { + content'\e0c9' +} + +.oi-text:before { + content'\e0ca' +} + +.oi-thumb-down:before { + content'\e0cb' +} + +.oi-thumb-up:before { + content'\e0cc' +} + +.oi-timer:before { + content'\e0cd' +} + +.oi-transfer:before { + content'\e0ce' +} + +.oi-trash:before { + content'\e0cf' +} + +.oi-underline:before { + content'\e0d0' +} + +.oi-vertical-align-bottom:before { + content'\e0d1' +} + +.oi-vertical-align-center:before { + content'\e0d2' +} + +.oi-vertical-align-top:before { + content'\e0d3' +} + +.oi-video:before { + content'\e0d4' +} + +.oi-volume-high:before { + content'\e0d5' +} + +.oi-volume-low:before { + content'\e0d6' +} + +.oi-volume-off:before { + content'\e0d7' +} + +.oi-warning:before { + content'\e0d8' +} + +.oi-wifi:before { + content'\e0d9' +} + +.oi-wrench:before { + content'\e0da' +} + +.oi-x:before { + content'\e0db' +} + +.oi-yen:before { + content'\e0dc' +} + +.oi-zoom-in:before { + content'\e0dd' +} + +.oi-zoom-out:before { + content'\e0de' +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.css b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.css new file mode 100644 index 00000000..905a8212 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.css @@ -0,0 +1,1395 @@ +/* Foundation */ + +@font-face { + font-family: 'Icons'; + src: url('../fonts/open-iconic.eot'); + src: url('../fonts/open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('../fonts/open-iconic.woff') format('woff'), url('../fonts/open-iconic.ttf') format('truetype'), url('../fonts/open-iconic.otf') format('opentype'), url('../fonts/open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + + +.fi-account-login:before, + +.fi-account-logout:before, + +.fi-action-redo:before, + +.fi-action-undo:before, + +.fi-align-center:before, + +.fi-align-left:before, + +.fi-align-right:before, + +.fi-aperture:before, + +.fi-arrow-bottom:before, + +.fi-arrow-circle-bottom:before, + +.fi-arrow-circle-left:before, + +.fi-arrow-circle-right:before, + +.fi-arrow-circle-top:before, + +.fi-arrow-left:before, + +.fi-arrow-right:before, + +.fi-arrow-thick-bottom:before, + +.fi-arrow-thick-left:before, + +.fi-arrow-thick-right:before, + +.fi-arrow-thick-top:before, + +.fi-arrow-top:before, + +.fi-audio-spectrum:before, + +.fi-audio:before, + +.fi-badge:before, + +.fi-ban:before, + +.fi-bar-chart:before, + +.fi-basket:before, + +.fi-battery-empty:before, + +.fi-battery-full:before, + +.fi-beaker:before, + +.fi-bell:before, + +.fi-bluetooth:before, + +.fi-bold:before, + +.fi-bolt:before, + +.fi-book:before, + +.fi-bookmark:before, + +.fi-box:before, + +.fi-briefcase:before, + +.fi-british-pound:before, + +.fi-browser:before, + +.fi-brush:before, + +.fi-bug:before, + +.fi-bullhorn:before, + +.fi-calculator:before, + +.fi-calendar:before, + +.fi-camera-slr:before, + +.fi-caret-bottom:before, + +.fi-caret-left:before, + +.fi-caret-right:before, + +.fi-caret-top:before, + +.fi-cart:before, + +.fi-chat:before, + +.fi-check:before, + +.fi-chevron-bottom:before, + +.fi-chevron-left:before, + +.fi-chevron-right:before, + +.fi-chevron-top:before, + +.fi-circle-check:before, + +.fi-circle-x:before, + +.fi-clipboard:before, + +.fi-clock:before, + +.fi-cloud-download:before, + +.fi-cloud-upload:before, + +.fi-cloud:before, + +.fi-cloudy:before, + +.fi-code:before, + +.fi-cog:before, + +.fi-collapse-down:before, + +.fi-collapse-left:before, + +.fi-collapse-right:before, + +.fi-collapse-up:before, + +.fi-command:before, + +.fi-comment-square:before, + +.fi-compass:before, + +.fi-contrast:before, + +.fi-copywriting:before, + +.fi-credit-card:before, + +.fi-crop:before, + +.fi-dashboard:before, + +.fi-data-transfer-download:before, + +.fi-data-transfer-upload:before, + +.fi-delete:before, + +.fi-dial:before, + +.fi-document:before, + +.fi-dollar:before, + +.fi-double-quote-sans-left:before, + +.fi-double-quote-sans-right:before, + +.fi-double-quote-serif-left:before, + +.fi-double-quote-serif-right:before, + +.fi-droplet:before, + +.fi-eject:before, + +.fi-elevator:before, + +.fi-ellipses:before, + +.fi-envelope-closed:before, + +.fi-envelope-open:before, + +.fi-euro:before, + +.fi-excerpt:before, + +.fi-expand-down:before, + +.fi-expand-left:before, + +.fi-expand-right:before, + +.fi-expand-up:before, + +.fi-external-link:before, + +.fi-eye:before, + +.fi-eyedropper:before, + +.fi-file:before, + +.fi-fire:before, + +.fi-flag:before, + +.fi-flash:before, + +.fi-folder:before, + +.fi-fork:before, + +.fi-fullscreen-enter:before, + +.fi-fullscreen-exit:before, + +.fi-globe:before, + +.fi-graph:before, + +.fi-grid-four-up:before, + +.fi-grid-three-up:before, + +.fi-grid-two-up:before, + +.fi-hard-drive:before, + +.fi-header:before, + +.fi-headphones:before, + +.fi-heart:before, + +.fi-home:before, + +.fi-image:before, + +.fi-inbox:before, + +.fi-infinity:before, + +.fi-info:before, + +.fi-italic:before, + +.fi-justify-center:before, + +.fi-justify-left:before, + +.fi-justify-right:before, + +.fi-key:before, + +.fi-laptop:before, + +.fi-layers:before, + +.fi-lightbulb:before, + +.fi-link-broken:before, + +.fi-link-intact:before, + +.fi-list-rich:before, + +.fi-list:before, + +.fi-location:before, + +.fi-lock-locked:before, + +.fi-lock-unlocked:before, + +.fi-loop-circular:before, + +.fi-loop-square:before, + +.fi-loop:before, + +.fi-magnifying-glass:before, + +.fi-map-marker:before, + +.fi-map:before, + +.fi-media-pause:before, + +.fi-media-play:before, + +.fi-media-record:before, + +.fi-media-skip-backward:before, + +.fi-media-skip-forward:before, + +.fi-media-step-backward:before, + +.fi-media-step-forward:before, + +.fi-media-stop:before, + +.fi-medical-cross:before, + +.fi-menu:before, + +.fi-microphone:before, + +.fi-minus:before, + +.fi-monitor:before, + +.fi-moon:before, + +.fi-move:before, + +.fi-musical-note:before, + +.fi-paperclip:before, + +.fi-pencil:before, + +.fi-people:before, + +.fi-person:before, + +.fi-phone:before, + +.fi-pie-chart:before, + +.fi-pin:before, + +.fi-play-circle:before, + +.fi-plus:before, + +.fi-power-standby:before, + +.fi-print:before, + +.fi-project:before, + +.fi-pulse:before, + +.fi-puzzle-piece:before, + +.fi-question-mark:before, + +.fi-rain:before, + +.fi-random:before, + +.fi-reload:before, + +.fi-resize-both:before, + +.fi-resize-height:before, + +.fi-resize-width:before, + +.fi-rss-alt:before, + +.fi-rss:before, + +.fi-script:before, + +.fi-share-boxed:before, + +.fi-share:before, + +.fi-shield:before, + +.fi-signal:before, + +.fi-signpost:before, + +.fi-sort-ascending:before, + +.fi-sort-descending:before, + +.fi-spreadsheet:before, + +.fi-star:before, + +.fi-sun:before, + +.fi-tablet:before, + +.fi-tag:before, + +.fi-tags:before, + +.fi-target:before, + +.fi-task:before, + +.fi-terminal:before, + +.fi-text:before, + +.fi-thumb-down:before, + +.fi-thumb-up:before, + +.fi-timer:before, + +.fi-transfer:before, + +.fi-trash:before, + +.fi-underline:before, + +.fi-vertical-align-bottom:before, + +.fi-vertical-align-center:before, + +.fi-vertical-align-top:before, + +.fi-video:before, + +.fi-volume-high:before, + +.fi-volume-low:before, + +.fi-volume-off:before, + +.fi-warning:before, + +.fi-wifi:before, + +.fi-wrench:before, + +.fi-x:before, + +.fi-yen:before, + +.fi-zoom-in:before, + +.fi-zoom-out:before + { + font-family: 'Icons'; + font-style: normal; + font-weight: normal; + font-variant: normal; + text-transform: none; + line-height: 1; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + display: inline-block; + text-decoration: inherit; +} + + +[class*='fi-'].oi-align-center:before { + text-align: center; +} + +[class*='fi-'].oi-align-left:before { + text-align: left; +} + +[class*='fi-'].oi-align-right:before { + text-align: right; +} + + +[class*='fi-'].oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} + +[class*='fi-'].oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); +} + +[class*='fi-'].oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); +} + + + +.fi-account-login:before { + content:'\e000'; +} + +.fi-account-logout:before { + content:'\e001'; +} + +.fi-action-redo:before { + content:'\e002'; +} + +.fi-action-undo:before { + content:'\e003'; +} + +.fi-align-center:before { + content:'\e004'; +} + +.fi-align-left:before { + content:'\e005'; +} + +.fi-align-right:before { + content:'\e006'; +} + +.fi-aperture:before { + content:'\e007'; +} + +.fi-arrow-bottom:before { + content:'\e008'; +} + +.fi-arrow-circle-bottom:before { + content:'\e009'; +} + +.fi-arrow-circle-left:before { + content:'\e00a'; +} + +.fi-arrow-circle-right:before { + content:'\e00b'; +} + +.fi-arrow-circle-top:before { + content:'\e00c'; +} + +.fi-arrow-left:before { + content:'\e00d'; +} + +.fi-arrow-right:before { + content:'\e00e'; +} + +.fi-arrow-thick-bottom:before { + content:'\e00f'; +} + +.fi-arrow-thick-left:before { + content:'\e010'; +} + +.fi-arrow-thick-right:before { + content:'\e011'; +} + +.fi-arrow-thick-top:before { + content:'\e012'; +} + +.fi-arrow-top:before { + content:'\e013'; +} + +.fi-audio-spectrum:before { + content:'\e014'; +} + +.fi-audio:before { + content:'\e015'; +} + +.fi-badge:before { + content:'\e016'; +} + +.fi-ban:before { + content:'\e017'; +} + +.fi-bar-chart:before { + content:'\e018'; +} + +.fi-basket:before { + content:'\e019'; +} + +.fi-battery-empty:before { + content:'\e01a'; +} + +.fi-battery-full:before { + content:'\e01b'; +} + +.fi-beaker:before { + content:'\e01c'; +} + +.fi-bell:before { + content:'\e01d'; +} + +.fi-bluetooth:before { + content:'\e01e'; +} + +.fi-bold:before { + content:'\e01f'; +} + +.fi-bolt:before { + content:'\e020'; +} + +.fi-book:before { + content:'\e021'; +} + +.fi-bookmark:before { + content:'\e022'; +} + +.fi-box:before { + content:'\e023'; +} + +.fi-briefcase:before { + content:'\e024'; +} + +.fi-british-pound:before { + content:'\e025'; +} + +.fi-browser:before { + content:'\e026'; +} + +.fi-brush:before { + content:'\e027'; +} + +.fi-bug:before { + content:'\e028'; +} + +.fi-bullhorn:before { + content:'\e029'; +} + +.fi-calculator:before { + content:'\e02a'; +} + +.fi-calendar:before { + content:'\e02b'; +} + +.fi-camera-slr:before { + content:'\e02c'; +} + +.fi-caret-bottom:before { + content:'\e02d'; +} + +.fi-caret-left:before { + content:'\e02e'; +} + +.fi-caret-right:before { + content:'\e02f'; +} + +.fi-caret-top:before { + content:'\e030'; +} + +.fi-cart:before { + content:'\e031'; +} + +.fi-chat:before { + content:'\e032'; +} + +.fi-check:before { + content:'\e033'; +} + +.fi-chevron-bottom:before { + content:'\e034'; +} + +.fi-chevron-left:before { + content:'\e035'; +} + +.fi-chevron-right:before { + content:'\e036'; +} + +.fi-chevron-top:before { + content:'\e037'; +} + +.fi-circle-check:before { + content:'\e038'; +} + +.fi-circle-x:before { + content:'\e039'; +} + +.fi-clipboard:before { + content:'\e03a'; +} + +.fi-clock:before { + content:'\e03b'; +} + +.fi-cloud-download:before { + content:'\e03c'; +} + +.fi-cloud-upload:before { + content:'\e03d'; +} + +.fi-cloud:before { + content:'\e03e'; +} + +.fi-cloudy:before { + content:'\e03f'; +} + +.fi-code:before { + content:'\e040'; +} + +.fi-cog:before { + content:'\e041'; +} + +.fi-collapse-down:before { + content:'\e042'; +} + +.fi-collapse-left:before { + content:'\e043'; +} + +.fi-collapse-right:before { + content:'\e044'; +} + +.fi-collapse-up:before { + content:'\e045'; +} + +.fi-command:before { + content:'\e046'; +} + +.fi-comment-square:before { + content:'\e047'; +} + +.fi-compass:before { + content:'\e048'; +} + +.fi-contrast:before { + content:'\e049'; +} + +.fi-copywriting:before { + content:'\e04a'; +} + +.fi-credit-card:before { + content:'\e04b'; +} + +.fi-crop:before { + content:'\e04c'; +} + +.fi-dashboard:before { + content:'\e04d'; +} + +.fi-data-transfer-download:before { + content:'\e04e'; +} + +.fi-data-transfer-upload:before { + content:'\e04f'; +} + +.fi-delete:before { + content:'\e050'; +} + +.fi-dial:before { + content:'\e051'; +} + +.fi-document:before { + content:'\e052'; +} + +.fi-dollar:before { + content:'\e053'; +} + +.fi-double-quote-sans-left:before { + content:'\e054'; +} + +.fi-double-quote-sans-right:before { + content:'\e055'; +} + +.fi-double-quote-serif-left:before { + content:'\e056'; +} + +.fi-double-quote-serif-right:before { + content:'\e057'; +} + +.fi-droplet:before { + content:'\e058'; +} + +.fi-eject:before { + content:'\e059'; +} + +.fi-elevator:before { + content:'\e05a'; +} + +.fi-ellipses:before { + content:'\e05b'; +} + +.fi-envelope-closed:before { + content:'\e05c'; +} + +.fi-envelope-open:before { + content:'\e05d'; +} + +.fi-euro:before { + content:'\e05e'; +} + +.fi-excerpt:before { + content:'\e05f'; +} + +.fi-expand-down:before { + content:'\e060'; +} + +.fi-expand-left:before { + content:'\e061'; +} + +.fi-expand-right:before { + content:'\e062'; +} + +.fi-expand-up:before { + content:'\e063'; +} + +.fi-external-link:before { + content:'\e064'; +} + +.fi-eye:before { + content:'\e065'; +} + +.fi-eyedropper:before { + content:'\e066'; +} + +.fi-file:before { + content:'\e067'; +} + +.fi-fire:before { + content:'\e068'; +} + +.fi-flag:before { + content:'\e069'; +} + +.fi-flash:before { + content:'\e06a'; +} + +.fi-folder:before { + content:'\e06b'; +} + +.fi-fork:before { + content:'\e06c'; +} + +.fi-fullscreen-enter:before { + content:'\e06d'; +} + +.fi-fullscreen-exit:before { + content:'\e06e'; +} + +.fi-globe:before { + content:'\e06f'; +} + +.fi-graph:before { + content:'\e070'; +} + +.fi-grid-four-up:before { + content:'\e071'; +} + +.fi-grid-three-up:before { + content:'\e072'; +} + +.fi-grid-two-up:before { + content:'\e073'; +} + +.fi-hard-drive:before { + content:'\e074'; +} + +.fi-header:before { + content:'\e075'; +} + +.fi-headphones:before { + content:'\e076'; +} + +.fi-heart:before { + content:'\e077'; +} + +.fi-home:before { + content:'\e078'; +} + +.fi-image:before { + content:'\e079'; +} + +.fi-inbox:before { + content:'\e07a'; +} + +.fi-infinity:before { + content:'\e07b'; +} + +.fi-info:before { + content:'\e07c'; +} + +.fi-italic:before { + content:'\e07d'; +} + +.fi-justify-center:before { + content:'\e07e'; +} + +.fi-justify-left:before { + content:'\e07f'; +} + +.fi-justify-right:before { + content:'\e080'; +} + +.fi-key:before { + content:'\e081'; +} + +.fi-laptop:before { + content:'\e082'; +} + +.fi-layers:before { + content:'\e083'; +} + +.fi-lightbulb:before { + content:'\e084'; +} + +.fi-link-broken:before { + content:'\e085'; +} + +.fi-link-intact:before { + content:'\e086'; +} + +.fi-list-rich:before { + content:'\e087'; +} + +.fi-list:before { + content:'\e088'; +} + +.fi-location:before { + content:'\e089'; +} + +.fi-lock-locked:before { + content:'\e08a'; +} + +.fi-lock-unlocked:before { + content:'\e08b'; +} + +.fi-loop-circular:before { + content:'\e08c'; +} + +.fi-loop-square:before { + content:'\e08d'; +} + +.fi-loop:before { + content:'\e08e'; +} + +.fi-magnifying-glass:before { + content:'\e08f'; +} + +.fi-map-marker:before { + content:'\e090'; +} + +.fi-map:before { + content:'\e091'; +} + +.fi-media-pause:before { + content:'\e092'; +} + +.fi-media-play:before { + content:'\e093'; +} + +.fi-media-record:before { + content:'\e094'; +} + +.fi-media-skip-backward:before { + content:'\e095'; +} + +.fi-media-skip-forward:before { + content:'\e096'; +} + +.fi-media-step-backward:before { + content:'\e097'; +} + +.fi-media-step-forward:before { + content:'\e098'; +} + +.fi-media-stop:before { + content:'\e099'; +} + +.fi-medical-cross:before { + content:'\e09a'; +} + +.fi-menu:before { + content:'\e09b'; +} + +.fi-microphone:before { + content:'\e09c'; +} + +.fi-minus:before { + content:'\e09d'; +} + +.fi-monitor:before { + content:'\e09e'; +} + +.fi-moon:before { + content:'\e09f'; +} + +.fi-move:before { + content:'\e0a0'; +} + +.fi-musical-note:before { + content:'\e0a1'; +} + +.fi-paperclip:before { + content:'\e0a2'; +} + +.fi-pencil:before { + content:'\e0a3'; +} + +.fi-people:before { + content:'\e0a4'; +} + +.fi-person:before { + content:'\e0a5'; +} + +.fi-phone:before { + content:'\e0a6'; +} + +.fi-pie-chart:before { + content:'\e0a7'; +} + +.fi-pin:before { + content:'\e0a8'; +} + +.fi-play-circle:before { + content:'\e0a9'; +} + +.fi-plus:before { + content:'\e0aa'; +} + +.fi-power-standby:before { + content:'\e0ab'; +} + +.fi-print:before { + content:'\e0ac'; +} + +.fi-project:before { + content:'\e0ad'; +} + +.fi-pulse:before { + content:'\e0ae'; +} + +.fi-puzzle-piece:before { + content:'\e0af'; +} + +.fi-question-mark:before { + content:'\e0b0'; +} + +.fi-rain:before { + content:'\e0b1'; +} + +.fi-random:before { + content:'\e0b2'; +} + +.fi-reload:before { + content:'\e0b3'; +} + +.fi-resize-both:before { + content:'\e0b4'; +} + +.fi-resize-height:before { + content:'\e0b5'; +} + +.fi-resize-width:before { + content:'\e0b6'; +} + +.fi-rss-alt:before { + content:'\e0b7'; +} + +.fi-rss:before { + content:'\e0b8'; +} + +.fi-script:before { + content:'\e0b9'; +} + +.fi-share-boxed:before { + content:'\e0ba'; +} + +.fi-share:before { + content:'\e0bb'; +} + +.fi-shield:before { + content:'\e0bc'; +} + +.fi-signal:before { + content:'\e0bd'; +} + +.fi-signpost:before { + content:'\e0be'; +} + +.fi-sort-ascending:before { + content:'\e0bf'; +} + +.fi-sort-descending:before { + content:'\e0c0'; +} + +.fi-spreadsheet:before { + content:'\e0c1'; +} + +.fi-star:before { + content:'\e0c2'; +} + +.fi-sun:before { + content:'\e0c3'; +} + +.fi-tablet:before { + content:'\e0c4'; +} + +.fi-tag:before { + content:'\e0c5'; +} + +.fi-tags:before { + content:'\e0c6'; +} + +.fi-target:before { + content:'\e0c7'; +} + +.fi-task:before { + content:'\e0c8'; +} + +.fi-terminal:before { + content:'\e0c9'; +} + +.fi-text:before { + content:'\e0ca'; +} + +.fi-thumb-down:before { + content:'\e0cb'; +} + +.fi-thumb-up:before { + content:'\e0cc'; +} + +.fi-timer:before { + content:'\e0cd'; +} + +.fi-transfer:before { + content:'\e0ce'; +} + +.fi-trash:before { + content:'\e0cf'; +} + +.fi-underline:before { + content:'\e0d0'; +} + +.fi-vertical-align-bottom:before { + content:'\e0d1'; +} + +.fi-vertical-align-center:before { + content:'\e0d2'; +} + +.fi-vertical-align-top:before { + content:'\e0d3'; +} + +.fi-video:before { + content:'\e0d4'; +} + +.fi-volume-high:before { + content:'\e0d5'; +} + +.fi-volume-low:before { + content:'\e0d6'; +} + +.fi-volume-off:before { + content:'\e0d7'; +} + +.fi-warning:before { + content:'\e0d8'; +} + +.fi-wifi:before { + content:'\e0d9'; +} + +.fi-wrench:before { + content:'\e0da'; +} + +.fi-x:before { + content:'\e0db'; +} + +.fi-yen:before { + content:'\e0dc'; +} + +.fi-zoom-in:before { + content:'\e0dd'; +} + +.fi-zoom-out:before { + content:'\e0de'; +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.less b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.less new file mode 100644 index 00000000..deabf26f --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.less @@ -0,0 +1,1397 @@ +/* Foundation */ + +/* Font path variable */ +@icon-font-path: '../fonts/'; + +@font-face { + font-family: 'Icons'; + src: url('@{icon-font-path}open-iconic.eot'); + src: url('@{icon-font-path}open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('@{icon-font-path}open-iconic.woff') format('woff'), url('@{icon-font-path}open-iconic.ttf') format('truetype'), url('@{icon-font-path}open-iconic.otf') format('opentype'), url('@{icon-font-path}open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + + +.fi-account-login:before, + +.fi-account-logout:before, + +.fi-action-redo:before, + +.fi-action-undo:before, + +.fi-align-center:before, + +.fi-align-left:before, + +.fi-align-right:before, + +.fi-aperture:before, + +.fi-arrow-bottom:before, + +.fi-arrow-circle-bottom:before, + +.fi-arrow-circle-left:before, + +.fi-arrow-circle-right:before, + +.fi-arrow-circle-top:before, + +.fi-arrow-left:before, + +.fi-arrow-right:before, + +.fi-arrow-thick-bottom:before, + +.fi-arrow-thick-left:before, + +.fi-arrow-thick-right:before, + +.fi-arrow-thick-top:before, + +.fi-arrow-top:before, + +.fi-audio-spectrum:before, + +.fi-audio:before, + +.fi-badge:before, + +.fi-ban:before, + +.fi-bar-chart:before, + +.fi-basket:before, + +.fi-battery-empty:before, + +.fi-battery-full:before, + +.fi-beaker:before, + +.fi-bell:before, + +.fi-bluetooth:before, + +.fi-bold:before, + +.fi-bolt:before, + +.fi-book:before, + +.fi-bookmark:before, + +.fi-box:before, + +.fi-briefcase:before, + +.fi-british-pound:before, + +.fi-browser:before, + +.fi-brush:before, + +.fi-bug:before, + +.fi-bullhorn:before, + +.fi-calculator:before, + +.fi-calendar:before, + +.fi-camera-slr:before, + +.fi-caret-bottom:before, + +.fi-caret-left:before, + +.fi-caret-right:before, + +.fi-caret-top:before, + +.fi-cart:before, + +.fi-chat:before, + +.fi-check:before, + +.fi-chevron-bottom:before, + +.fi-chevron-left:before, + +.fi-chevron-right:before, + +.fi-chevron-top:before, + +.fi-circle-check:before, + +.fi-circle-x:before, + +.fi-clipboard:before, + +.fi-clock:before, + +.fi-cloud-download:before, + +.fi-cloud-upload:before, + +.fi-cloud:before, + +.fi-cloudy:before, + +.fi-code:before, + +.fi-cog:before, + +.fi-collapse-down:before, + +.fi-collapse-left:before, + +.fi-collapse-right:before, + +.fi-collapse-up:before, + +.fi-command:before, + +.fi-comment-square:before, + +.fi-compass:before, + +.fi-contrast:before, + +.fi-copywriting:before, + +.fi-credit-card:before, + +.fi-crop:before, + +.fi-dashboard:before, + +.fi-data-transfer-download:before, + +.fi-data-transfer-upload:before, + +.fi-delete:before, + +.fi-dial:before, + +.fi-document:before, + +.fi-dollar:before, + +.fi-double-quote-sans-left:before, + +.fi-double-quote-sans-right:before, + +.fi-double-quote-serif-left:before, + +.fi-double-quote-serif-right:before, + +.fi-droplet:before, + +.fi-eject:before, + +.fi-elevator:before, + +.fi-ellipses:before, + +.fi-envelope-closed:before, + +.fi-envelope-open:before, + +.fi-euro:before, + +.fi-excerpt:before, + +.fi-expand-down:before, + +.fi-expand-left:before, + +.fi-expand-right:before, + +.fi-expand-up:before, + +.fi-external-link:before, + +.fi-eye:before, + +.fi-eyedropper:before, + +.fi-file:before, + +.fi-fire:before, + +.fi-flag:before, + +.fi-flash:before, + +.fi-folder:before, + +.fi-fork:before, + +.fi-fullscreen-enter:before, + +.fi-fullscreen-exit:before, + +.fi-globe:before, + +.fi-graph:before, + +.fi-grid-four-up:before, + +.fi-grid-three-up:before, + +.fi-grid-two-up:before, + +.fi-hard-drive:before, + +.fi-header:before, + +.fi-headphones:before, + +.fi-heart:before, + +.fi-home:before, + +.fi-image:before, + +.fi-inbox:before, + +.fi-infinity:before, + +.fi-info:before, + +.fi-italic:before, + +.fi-justify-center:before, + +.fi-justify-left:before, + +.fi-justify-right:before, + +.fi-key:before, + +.fi-laptop:before, + +.fi-layers:before, + +.fi-lightbulb:before, + +.fi-link-broken:before, + +.fi-link-intact:before, + +.fi-list-rich:before, + +.fi-list:before, + +.fi-location:before, + +.fi-lock-locked:before, + +.fi-lock-unlocked:before, + +.fi-loop-circular:before, + +.fi-loop-square:before, + +.fi-loop:before, + +.fi-magnifying-glass:before, + +.fi-map-marker:before, + +.fi-map:before, + +.fi-media-pause:before, + +.fi-media-play:before, + +.fi-media-record:before, + +.fi-media-skip-backward:before, + +.fi-media-skip-forward:before, + +.fi-media-step-backward:before, + +.fi-media-step-forward:before, + +.fi-media-stop:before, + +.fi-medical-cross:before, + +.fi-menu:before, + +.fi-microphone:before, + +.fi-minus:before, + +.fi-monitor:before, + +.fi-moon:before, + +.fi-move:before, + +.fi-musical-note:before, + +.fi-paperclip:before, + +.fi-pencil:before, + +.fi-people:before, + +.fi-person:before, + +.fi-phone:before, + +.fi-pie-chart:before, + +.fi-pin:before, + +.fi-play-circle:before, + +.fi-plus:before, + +.fi-power-standby:before, + +.fi-print:before, + +.fi-project:before, + +.fi-pulse:before, + +.fi-puzzle-piece:before, + +.fi-question-mark:before, + +.fi-rain:before, + +.fi-random:before, + +.fi-reload:before, + +.fi-resize-both:before, + +.fi-resize-height:before, + +.fi-resize-width:before, + +.fi-rss-alt:before, + +.fi-rss:before, + +.fi-script:before, + +.fi-share-boxed:before, + +.fi-share:before, + +.fi-shield:before, + +.fi-signal:before, + +.fi-signpost:before, + +.fi-sort-ascending:before, + +.fi-sort-descending:before, + +.fi-spreadsheet:before, + +.fi-star:before, + +.fi-sun:before, + +.fi-tablet:before, + +.fi-tag:before, + +.fi-tags:before, + +.fi-target:before, + +.fi-task:before, + +.fi-terminal:before, + +.fi-text:before, + +.fi-thumb-down:before, + +.fi-thumb-up:before, + +.fi-timer:before, + +.fi-transfer:before, + +.fi-trash:before, + +.fi-underline:before, + +.fi-vertical-align-bottom:before, + +.fi-vertical-align-center:before, + +.fi-vertical-align-top:before, + +.fi-video:before, + +.fi-volume-high:before, + +.fi-volume-low:before, + +.fi-volume-off:before, + +.fi-warning:before, + +.fi-wifi:before, + +.fi-wrench:before, + +.fi-x:before, + +.fi-yen:before, + +.fi-zoom-in:before, + +.fi-zoom-out:before + { + font-family: 'Icons'; + font-style: normal; + font-weight: normal; + font-variant: normal; + text-transform: none; + line-height: 1; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + display: inline-block; + text-decoration: inherit; +} + +[class*='fi-'].oi-align-center:before { + text-align: center; +} + +[class*='fi-'].oi-align-left:before { + text-align: left; +} + +[class*='fi-'].oi-align-right:before { + text-align: right; +} + + +[class*='fi-'].oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} + +[class*='fi-'].oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); +} + +[class*='fi-'].oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); +} + + + +.fi-account-login:before { + content:'\e000'; +} + +.fi-account-logout:before { + content:'\e001'; +} + +.fi-action-redo:before { + content:'\e002'; +} + +.fi-action-undo:before { + content:'\e003'; +} + +.fi-align-center:before { + content:'\e004'; +} + +.fi-align-left:before { + content:'\e005'; +} + +.fi-align-right:before { + content:'\e006'; +} + +.fi-aperture:before { + content:'\e007'; +} + +.fi-arrow-bottom:before { + content:'\e008'; +} + +.fi-arrow-circle-bottom:before { + content:'\e009'; +} + +.fi-arrow-circle-left:before { + content:'\e00a'; +} + +.fi-arrow-circle-right:before { + content:'\e00b'; +} + +.fi-arrow-circle-top:before { + content:'\e00c'; +} + +.fi-arrow-left:before { + content:'\e00d'; +} + +.fi-arrow-right:before { + content:'\e00e'; +} + +.fi-arrow-thick-bottom:before { + content:'\e00f'; +} + +.fi-arrow-thick-left:before { + content:'\e010'; +} + +.fi-arrow-thick-right:before { + content:'\e011'; +} + +.fi-arrow-thick-top:before { + content:'\e012'; +} + +.fi-arrow-top:before { + content:'\e013'; +} + +.fi-audio-spectrum:before { + content:'\e014'; +} + +.fi-audio:before { + content:'\e015'; +} + +.fi-badge:before { + content:'\e016'; +} + +.fi-ban:before { + content:'\e017'; +} + +.fi-bar-chart:before { + content:'\e018'; +} + +.fi-basket:before { + content:'\e019'; +} + +.fi-battery-empty:before { + content:'\e01a'; +} + +.fi-battery-full:before { + content:'\e01b'; +} + +.fi-beaker:before { + content:'\e01c'; +} + +.fi-bell:before { + content:'\e01d'; +} + +.fi-bluetooth:before { + content:'\e01e'; +} + +.fi-bold:before { + content:'\e01f'; +} + +.fi-bolt:before { + content:'\e020'; +} + +.fi-book:before { + content:'\e021'; +} + +.fi-bookmark:before { + content:'\e022'; +} + +.fi-box:before { + content:'\e023'; +} + +.fi-briefcase:before { + content:'\e024'; +} + +.fi-british-pound:before { + content:'\e025'; +} + +.fi-browser:before { + content:'\e026'; +} + +.fi-brush:before { + content:'\e027'; +} + +.fi-bug:before { + content:'\e028'; +} + +.fi-bullhorn:before { + content:'\e029'; +} + +.fi-calculator:before { + content:'\e02a'; +} + +.fi-calendar:before { + content:'\e02b'; +} + +.fi-camera-slr:before { + content:'\e02c'; +} + +.fi-caret-bottom:before { + content:'\e02d'; +} + +.fi-caret-left:before { + content:'\e02e'; +} + +.fi-caret-right:before { + content:'\e02f'; +} + +.fi-caret-top:before { + content:'\e030'; +} + +.fi-cart:before { + content:'\e031'; +} + +.fi-chat:before { + content:'\e032'; +} + +.fi-check:before { + content:'\e033'; +} + +.fi-chevron-bottom:before { + content:'\e034'; +} + +.fi-chevron-left:before { + content:'\e035'; +} + +.fi-chevron-right:before { + content:'\e036'; +} + +.fi-chevron-top:before { + content:'\e037'; +} + +.fi-circle-check:before { + content:'\e038'; +} + +.fi-circle-x:before { + content:'\e039'; +} + +.fi-clipboard:before { + content:'\e03a'; +} + +.fi-clock:before { + content:'\e03b'; +} + +.fi-cloud-download:before { + content:'\e03c'; +} + +.fi-cloud-upload:before { + content:'\e03d'; +} + +.fi-cloud:before { + content:'\e03e'; +} + +.fi-cloudy:before { + content:'\e03f'; +} + +.fi-code:before { + content:'\e040'; +} + +.fi-cog:before { + content:'\e041'; +} + +.fi-collapse-down:before { + content:'\e042'; +} + +.fi-collapse-left:before { + content:'\e043'; +} + +.fi-collapse-right:before { + content:'\e044'; +} + +.fi-collapse-up:before { + content:'\e045'; +} + +.fi-command:before { + content:'\e046'; +} + +.fi-comment-square:before { + content:'\e047'; +} + +.fi-compass:before { + content:'\e048'; +} + +.fi-contrast:before { + content:'\e049'; +} + +.fi-copywriting:before { + content:'\e04a'; +} + +.fi-credit-card:before { + content:'\e04b'; +} + +.fi-crop:before { + content:'\e04c'; +} + +.fi-dashboard:before { + content:'\e04d'; +} + +.fi-data-transfer-download:before { + content:'\e04e'; +} + +.fi-data-transfer-upload:before { + content:'\e04f'; +} + +.fi-delete:before { + content:'\e050'; +} + +.fi-dial:before { + content:'\e051'; +} + +.fi-document:before { + content:'\e052'; +} + +.fi-dollar:before { + content:'\e053'; +} + +.fi-double-quote-sans-left:before { + content:'\e054'; +} + +.fi-double-quote-sans-right:before { + content:'\e055'; +} + +.fi-double-quote-serif-left:before { + content:'\e056'; +} + +.fi-double-quote-serif-right:before { + content:'\e057'; +} + +.fi-droplet:before { + content:'\e058'; +} + +.fi-eject:before { + content:'\e059'; +} + +.fi-elevator:before { + content:'\e05a'; +} + +.fi-ellipses:before { + content:'\e05b'; +} + +.fi-envelope-closed:before { + content:'\e05c'; +} + +.fi-envelope-open:before { + content:'\e05d'; +} + +.fi-euro:before { + content:'\e05e'; +} + +.fi-excerpt:before { + content:'\e05f'; +} + +.fi-expand-down:before { + content:'\e060'; +} + +.fi-expand-left:before { + content:'\e061'; +} + +.fi-expand-right:before { + content:'\e062'; +} + +.fi-expand-up:before { + content:'\e063'; +} + +.fi-external-link:before { + content:'\e064'; +} + +.fi-eye:before { + content:'\e065'; +} + +.fi-eyedropper:before { + content:'\e066'; +} + +.fi-file:before { + content:'\e067'; +} + +.fi-fire:before { + content:'\e068'; +} + +.fi-flag:before { + content:'\e069'; +} + +.fi-flash:before { + content:'\e06a'; +} + +.fi-folder:before { + content:'\e06b'; +} + +.fi-fork:before { + content:'\e06c'; +} + +.fi-fullscreen-enter:before { + content:'\e06d'; +} + +.fi-fullscreen-exit:before { + content:'\e06e'; +} + +.fi-globe:before { + content:'\e06f'; +} + +.fi-graph:before { + content:'\e070'; +} + +.fi-grid-four-up:before { + content:'\e071'; +} + +.fi-grid-three-up:before { + content:'\e072'; +} + +.fi-grid-two-up:before { + content:'\e073'; +} + +.fi-hard-drive:before { + content:'\e074'; +} + +.fi-header:before { + content:'\e075'; +} + +.fi-headphones:before { + content:'\e076'; +} + +.fi-heart:before { + content:'\e077'; +} + +.fi-home:before { + content:'\e078'; +} + +.fi-image:before { + content:'\e079'; +} + +.fi-inbox:before { + content:'\e07a'; +} + +.fi-infinity:before { + content:'\e07b'; +} + +.fi-info:before { + content:'\e07c'; +} + +.fi-italic:before { + content:'\e07d'; +} + +.fi-justify-center:before { + content:'\e07e'; +} + +.fi-justify-left:before { + content:'\e07f'; +} + +.fi-justify-right:before { + content:'\e080'; +} + +.fi-key:before { + content:'\e081'; +} + +.fi-laptop:before { + content:'\e082'; +} + +.fi-layers:before { + content:'\e083'; +} + +.fi-lightbulb:before { + content:'\e084'; +} + +.fi-link-broken:before { + content:'\e085'; +} + +.fi-link-intact:before { + content:'\e086'; +} + +.fi-list-rich:before { + content:'\e087'; +} + +.fi-list:before { + content:'\e088'; +} + +.fi-location:before { + content:'\e089'; +} + +.fi-lock-locked:before { + content:'\e08a'; +} + +.fi-lock-unlocked:before { + content:'\e08b'; +} + +.fi-loop-circular:before { + content:'\e08c'; +} + +.fi-loop-square:before { + content:'\e08d'; +} + +.fi-loop:before { + content:'\e08e'; +} + +.fi-magnifying-glass:before { + content:'\e08f'; +} + +.fi-map-marker:before { + content:'\e090'; +} + +.fi-map:before { + content:'\e091'; +} + +.fi-media-pause:before { + content:'\e092'; +} + +.fi-media-play:before { + content:'\e093'; +} + +.fi-media-record:before { + content:'\e094'; +} + +.fi-media-skip-backward:before { + content:'\e095'; +} + +.fi-media-skip-forward:before { + content:'\e096'; +} + +.fi-media-step-backward:before { + content:'\e097'; +} + +.fi-media-step-forward:before { + content:'\e098'; +} + +.fi-media-stop:before { + content:'\e099'; +} + +.fi-medical-cross:before { + content:'\e09a'; +} + +.fi-menu:before { + content:'\e09b'; +} + +.fi-microphone:before { + content:'\e09c'; +} + +.fi-minus:before { + content:'\e09d'; +} + +.fi-monitor:before { + content:'\e09e'; +} + +.fi-moon:before { + content:'\e09f'; +} + +.fi-move:before { + content:'\e0a0'; +} + +.fi-musical-note:before { + content:'\e0a1'; +} + +.fi-paperclip:before { + content:'\e0a2'; +} + +.fi-pencil:before { + content:'\e0a3'; +} + +.fi-people:before { + content:'\e0a4'; +} + +.fi-person:before { + content:'\e0a5'; +} + +.fi-phone:before { + content:'\e0a6'; +} + +.fi-pie-chart:before { + content:'\e0a7'; +} + +.fi-pin:before { + content:'\e0a8'; +} + +.fi-play-circle:before { + content:'\e0a9'; +} + +.fi-plus:before { + content:'\e0aa'; +} + +.fi-power-standby:before { + content:'\e0ab'; +} + +.fi-print:before { + content:'\e0ac'; +} + +.fi-project:before { + content:'\e0ad'; +} + +.fi-pulse:before { + content:'\e0ae'; +} + +.fi-puzzle-piece:before { + content:'\e0af'; +} + +.fi-question-mark:before { + content:'\e0b0'; +} + +.fi-rain:before { + content:'\e0b1'; +} + +.fi-random:before { + content:'\e0b2'; +} + +.fi-reload:before { + content:'\e0b3'; +} + +.fi-resize-both:before { + content:'\e0b4'; +} + +.fi-resize-height:before { + content:'\e0b5'; +} + +.fi-resize-width:before { + content:'\e0b6'; +} + +.fi-rss-alt:before { + content:'\e0b7'; +} + +.fi-rss:before { + content:'\e0b8'; +} + +.fi-script:before { + content:'\e0b9'; +} + +.fi-share-boxed:before { + content:'\e0ba'; +} + +.fi-share:before { + content:'\e0bb'; +} + +.fi-shield:before { + content:'\e0bc'; +} + +.fi-signal:before { + content:'\e0bd'; +} + +.fi-signpost:before { + content:'\e0be'; +} + +.fi-sort-ascending:before { + content:'\e0bf'; +} + +.fi-sort-descending:before { + content:'\e0c0'; +} + +.fi-spreadsheet:before { + content:'\e0c1'; +} + +.fi-star:before { + content:'\e0c2'; +} + +.fi-sun:before { + content:'\e0c3'; +} + +.fi-tablet:before { + content:'\e0c4'; +} + +.fi-tag:before { + content:'\e0c5'; +} + +.fi-tags:before { + content:'\e0c6'; +} + +.fi-target:before { + content:'\e0c7'; +} + +.fi-task:before { + content:'\e0c8'; +} + +.fi-terminal:before { + content:'\e0c9'; +} + +.fi-text:before { + content:'\e0ca'; +} + +.fi-thumb-down:before { + content:'\e0cb'; +} + +.fi-thumb-up:before { + content:'\e0cc'; +} + +.fi-timer:before { + content:'\e0cd'; +} + +.fi-transfer:before { + content:'\e0ce'; +} + +.fi-trash:before { + content:'\e0cf'; +} + +.fi-underline:before { + content:'\e0d0'; +} + +.fi-vertical-align-bottom:before { + content:'\e0d1'; +} + +.fi-vertical-align-center:before { + content:'\e0d2'; +} + +.fi-vertical-align-top:before { + content:'\e0d3'; +} + +.fi-video:before { + content:'\e0d4'; +} + +.fi-volume-high:before { + content:'\e0d5'; +} + +.fi-volume-low:before { + content:'\e0d6'; +} + +.fi-volume-off:before { + content:'\e0d7'; +} + +.fi-warning:before { + content:'\e0d8'; +} + +.fi-wifi:before { + content:'\e0d9'; +} + +.fi-wrench:before { + content:'\e0da'; +} + +.fi-x:before { + content:'\e0db'; +} + +.fi-yen:before { + content:'\e0dc'; +} + +.fi-zoom-in:before { + content:'\e0dd'; +} + +.fi-zoom-out:before { + content:'\e0de'; +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.min.css b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.min.css new file mode 100644 index 00000000..bd124297 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.min.css @@ -0,0 +1 @@ +@font-face{font-family:Icons;src:url(../fonts/open-iconic.eot);src:url(../fonts/open-iconic.eot?#iconic-sm) format('embedded-opentype'),url(../fonts/open-iconic.woff) format('woff'),url(../fonts/open-iconic.ttf) format('truetype'),url(../fonts/open-iconic.otf) format('opentype'),url(../fonts/open-iconic.svg#iconic-sm) format('svg');font-weight:400;font-style:normal}.fi-account-login:before,.fi-account-logout:before,.fi-action-redo:before,.fi-action-undo:before,.fi-align-center:before,.fi-align-left:before,.fi-align-right:before,.fi-aperture:before,.fi-arrow-bottom:before,.fi-arrow-circle-bottom:before,.fi-arrow-circle-left:before,.fi-arrow-circle-right:before,.fi-arrow-circle-top:before,.fi-arrow-left:before,.fi-arrow-right:before,.fi-arrow-thick-bottom:before,.fi-arrow-thick-left:before,.fi-arrow-thick-right:before,.fi-arrow-thick-top:before,.fi-arrow-top:before,.fi-audio-spectrum:before,.fi-audio:before,.fi-badge:before,.fi-ban:before,.fi-bar-chart:before,.fi-basket:before,.fi-battery-empty:before,.fi-battery-full:before,.fi-beaker:before,.fi-bell:before,.fi-bluetooth:before,.fi-bold:before,.fi-bolt:before,.fi-book:before,.fi-bookmark:before,.fi-box:before,.fi-briefcase:before,.fi-british-pound:before,.fi-browser:before,.fi-brush:before,.fi-bug:before,.fi-bullhorn:before,.fi-calculator:before,.fi-calendar:before,.fi-camera-slr:before,.fi-caret-bottom:before,.fi-caret-left:before,.fi-caret-right:before,.fi-caret-top:before,.fi-cart:before,.fi-chat:before,.fi-check:before,.fi-chevron-bottom:before,.fi-chevron-left:before,.fi-chevron-right:before,.fi-chevron-top:before,.fi-circle-check:before,.fi-circle-x:before,.fi-clipboard:before,.fi-clock:before,.fi-cloud-download:before,.fi-cloud-upload:before,.fi-cloud:before,.fi-cloudy:before,.fi-code:before,.fi-cog:before,.fi-collapse-down:before,.fi-collapse-left:before,.fi-collapse-right:before,.fi-collapse-up:before,.fi-command:before,.fi-comment-square:before,.fi-compass:before,.fi-contrast:before,.fi-copywriting:before,.fi-credit-card:before,.fi-crop:before,.fi-dashboard:before,.fi-data-transfer-download:before,.fi-data-transfer-upload:before,.fi-delete:before,.fi-dial:before,.fi-document:before,.fi-dollar:before,.fi-double-quote-sans-left:before,.fi-double-quote-sans-right:before,.fi-double-quote-serif-left:before,.fi-double-quote-serif-right:before,.fi-droplet:before,.fi-eject:before,.fi-elevator:before,.fi-ellipses:before,.fi-envelope-closed:before,.fi-envelope-open:before,.fi-euro:before,.fi-excerpt:before,.fi-expand-down:before,.fi-expand-left:before,.fi-expand-right:before,.fi-expand-up:before,.fi-external-link:before,.fi-eye:before,.fi-eyedropper:before,.fi-file:before,.fi-fire:before,.fi-flag:before,.fi-flash:before,.fi-folder:before,.fi-fork:before,.fi-fullscreen-enter:before,.fi-fullscreen-exit:before,.fi-globe:before,.fi-graph:before,.fi-grid-four-up:before,.fi-grid-three-up:before,.fi-grid-two-up:before,.fi-hard-drive:before,.fi-header:before,.fi-headphones:before,.fi-heart:before,.fi-home:before,.fi-image:before,.fi-inbox:before,.fi-infinity:before,.fi-info:before,.fi-italic:before,.fi-justify-center:before,.fi-justify-left:before,.fi-justify-right:before,.fi-key:before,.fi-laptop:before,.fi-layers:before,.fi-lightbulb:before,.fi-link-broken:before,.fi-link-intact:before,.fi-list-rich:before,.fi-list:before,.fi-location:before,.fi-lock-locked:before,.fi-lock-unlocked:before,.fi-loop-circular:before,.fi-loop-square:before,.fi-loop:before,.fi-magnifying-glass:before,.fi-map-marker:before,.fi-map:before,.fi-media-pause:before,.fi-media-play:before,.fi-media-record:before,.fi-media-skip-backward:before,.fi-media-skip-forward:before,.fi-media-step-backward:before,.fi-media-step-forward:before,.fi-media-stop:before,.fi-medical-cross:before,.fi-menu:before,.fi-microphone:before,.fi-minus:before,.fi-monitor:before,.fi-moon:before,.fi-move:before,.fi-musical-note:before,.fi-paperclip:before,.fi-pencil:before,.fi-people:before,.fi-person:before,.fi-phone:before,.fi-pie-chart:before,.fi-pin:before,.fi-play-circle:before,.fi-plus:before,.fi-power-standby:before,.fi-print:before,.fi-project:before,.fi-pulse:before,.fi-puzzle-piece:before,.fi-question-mark:before,.fi-rain:before,.fi-random:before,.fi-reload:before,.fi-resize-both:before,.fi-resize-height:before,.fi-resize-width:before,.fi-rss-alt:before,.fi-rss:before,.fi-script:before,.fi-share-boxed:before,.fi-share:before,.fi-shield:before,.fi-signal:before,.fi-signpost:before,.fi-sort-ascending:before,.fi-sort-descending:before,.fi-spreadsheet:before,.fi-star:before,.fi-sun:before,.fi-tablet:before,.fi-tag:before,.fi-tags:before,.fi-target:before,.fi-task:before,.fi-terminal:before,.fi-text:before,.fi-thumb-down:before,.fi-thumb-up:before,.fi-timer:before,.fi-transfer:before,.fi-trash:before,.fi-underline:before,.fi-vertical-align-bottom:before,.fi-vertical-align-center:before,.fi-vertical-align-top:before,.fi-video:before,.fi-volume-high:before,.fi-volume-low:before,.fi-volume-off:before,.fi-warning:before,.fi-wifi:before,.fi-wrench:before,.fi-x:before,.fi-yen:before,.fi-zoom-in:before,.fi-zoom-out:before{font-family:Icons;font-style:normal;font-weight:400;font-variant:normal;text-transform:none;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;display:inline-block;text-decoration:inherit}[class*=fi-].oi-align-center:before{text-align:center}[class*=fi-].oi-align-left:before{text-align:left}[class*=fi-].oi-align-right:before{text-align:right}[class*=fi-].oi-flip-horizontal:before{-webkit-transform:scale(-1,1);-ms-transform:scale(-1,1);transform:scale(-1,1)}[class*=fi-].oi-flip-vertical:before{-webkit-transform:scale(1,-1);-ms-transform:scale(-1,1);transform:scale(1,-1)}[class*=fi-].oi-flip-horizontal-vertical:before{-webkit-transform:scale(-1,-1);-ms-transform:scale(-1,1);transform:scale(-1,-1)}.fi-account-login:before{content:'\e000'}.fi-account-logout:before{content:'\e001'}.fi-action-redo:before{content:'\e002'}.fi-action-undo:before{content:'\e003'}.fi-align-center:before{content:'\e004'}.fi-align-left:before{content:'\e005'}.fi-align-right:before{content:'\e006'}.fi-aperture:before{content:'\e007'}.fi-arrow-bottom:before{content:'\e008'}.fi-arrow-circle-bottom:before{content:'\e009'}.fi-arrow-circle-left:before{content:'\e00a'}.fi-arrow-circle-right:before{content:'\e00b'}.fi-arrow-circle-top:before{content:'\e00c'}.fi-arrow-left:before{content:'\e00d'}.fi-arrow-right:before{content:'\e00e'}.fi-arrow-thick-bottom:before{content:'\e00f'}.fi-arrow-thick-left:before{content:'\e010'}.fi-arrow-thick-right:before{content:'\e011'}.fi-arrow-thick-top:before{content:'\e012'}.fi-arrow-top:before{content:'\e013'}.fi-audio-spectrum:before{content:'\e014'}.fi-audio:before{content:'\e015'}.fi-badge:before{content:'\e016'}.fi-ban:before{content:'\e017'}.fi-bar-chart:before{content:'\e018'}.fi-basket:before{content:'\e019'}.fi-battery-empty:before{content:'\e01a'}.fi-battery-full:before{content:'\e01b'}.fi-beaker:before{content:'\e01c'}.fi-bell:before{content:'\e01d'}.fi-bluetooth:before{content:'\e01e'}.fi-bold:before{content:'\e01f'}.fi-bolt:before{content:'\e020'}.fi-book:before{content:'\e021'}.fi-bookmark:before{content:'\e022'}.fi-box:before{content:'\e023'}.fi-briefcase:before{content:'\e024'}.fi-british-pound:before{content:'\e025'}.fi-browser:before{content:'\e026'}.fi-brush:before{content:'\e027'}.fi-bug:before{content:'\e028'}.fi-bullhorn:before{content:'\e029'}.fi-calculator:before{content:'\e02a'}.fi-calendar:before{content:'\e02b'}.fi-camera-slr:before{content:'\e02c'}.fi-caret-bottom:before{content:'\e02d'}.fi-caret-left:before{content:'\e02e'}.fi-caret-right:before{content:'\e02f'}.fi-caret-top:before{content:'\e030'}.fi-cart:before{content:'\e031'}.fi-chat:before{content:'\e032'}.fi-check:before{content:'\e033'}.fi-chevron-bottom:before{content:'\e034'}.fi-chevron-left:before{content:'\e035'}.fi-chevron-right:before{content:'\e036'}.fi-chevron-top:before{content:'\e037'}.fi-circle-check:before{content:'\e038'}.fi-circle-x:before{content:'\e039'}.fi-clipboard:before{content:'\e03a'}.fi-clock:before{content:'\e03b'}.fi-cloud-download:before{content:'\e03c'}.fi-cloud-upload:before{content:'\e03d'}.fi-cloud:before{content:'\e03e'}.fi-cloudy:before{content:'\e03f'}.fi-code:before{content:'\e040'}.fi-cog:before{content:'\e041'}.fi-collapse-down:before{content:'\e042'}.fi-collapse-left:before{content:'\e043'}.fi-collapse-right:before{content:'\e044'}.fi-collapse-up:before{content:'\e045'}.fi-command:before{content:'\e046'}.fi-comment-square:before{content:'\e047'}.fi-compass:before{content:'\e048'}.fi-contrast:before{content:'\e049'}.fi-copywriting:before{content:'\e04a'}.fi-credit-card:before{content:'\e04b'}.fi-crop:before{content:'\e04c'}.fi-dashboard:before{content:'\e04d'}.fi-data-transfer-download:before{content:'\e04e'}.fi-data-transfer-upload:before{content:'\e04f'}.fi-delete:before{content:'\e050'}.fi-dial:before{content:'\e051'}.fi-document:before{content:'\e052'}.fi-dollar:before{content:'\e053'}.fi-double-quote-sans-left:before{content:'\e054'}.fi-double-quote-sans-right:before{content:'\e055'}.fi-double-quote-serif-left:before{content:'\e056'}.fi-double-quote-serif-right:before{content:'\e057'}.fi-droplet:before{content:'\e058'}.fi-eject:before{content:'\e059'}.fi-elevator:before{content:'\e05a'}.fi-ellipses:before{content:'\e05b'}.fi-envelope-closed:before{content:'\e05c'}.fi-envelope-open:before{content:'\e05d'}.fi-euro:before{content:'\e05e'}.fi-excerpt:before{content:'\e05f'}.fi-expand-down:before{content:'\e060'}.fi-expand-left:before{content:'\e061'}.fi-expand-right:before{content:'\e062'}.fi-expand-up:before{content:'\e063'}.fi-external-link:before{content:'\e064'}.fi-eye:before{content:'\e065'}.fi-eyedropper:before{content:'\e066'}.fi-file:before{content:'\e067'}.fi-fire:before{content:'\e068'}.fi-flag:before{content:'\e069'}.fi-flash:before{content:'\e06a'}.fi-folder:before{content:'\e06b'}.fi-fork:before{content:'\e06c'}.fi-fullscreen-enter:before{content:'\e06d'}.fi-fullscreen-exit:before{content:'\e06e'}.fi-globe:before{content:'\e06f'}.fi-graph:before{content:'\e070'}.fi-grid-four-up:before{content:'\e071'}.fi-grid-three-up:before{content:'\e072'}.fi-grid-two-up:before{content:'\e073'}.fi-hard-drive:before{content:'\e074'}.fi-header:before{content:'\e075'}.fi-headphones:before{content:'\e076'}.fi-heart:before{content:'\e077'}.fi-home:before{content:'\e078'}.fi-image:before{content:'\e079'}.fi-inbox:before{content:'\e07a'}.fi-infinity:before{content:'\e07b'}.fi-info:before{content:'\e07c'}.fi-italic:before{content:'\e07d'}.fi-justify-center:before{content:'\e07e'}.fi-justify-left:before{content:'\e07f'}.fi-justify-right:before{content:'\e080'}.fi-key:before{content:'\e081'}.fi-laptop:before{content:'\e082'}.fi-layers:before{content:'\e083'}.fi-lightbulb:before{content:'\e084'}.fi-link-broken:before{content:'\e085'}.fi-link-intact:before{content:'\e086'}.fi-list-rich:before{content:'\e087'}.fi-list:before{content:'\e088'}.fi-location:before{content:'\e089'}.fi-lock-locked:before{content:'\e08a'}.fi-lock-unlocked:before{content:'\e08b'}.fi-loop-circular:before{content:'\e08c'}.fi-loop-square:before{content:'\e08d'}.fi-loop:before{content:'\e08e'}.fi-magnifying-glass:before{content:'\e08f'}.fi-map-marker:before{content:'\e090'}.fi-map:before{content:'\e091'}.fi-media-pause:before{content:'\e092'}.fi-media-play:before{content:'\e093'}.fi-media-record:before{content:'\e094'}.fi-media-skip-backward:before{content:'\e095'}.fi-media-skip-forward:before{content:'\e096'}.fi-media-step-backward:before{content:'\e097'}.fi-media-step-forward:before{content:'\e098'}.fi-media-stop:before{content:'\e099'}.fi-medical-cross:before{content:'\e09a'}.fi-menu:before{content:'\e09b'}.fi-microphone:before{content:'\e09c'}.fi-minus:before{content:'\e09d'}.fi-monitor:before{content:'\e09e'}.fi-moon:before{content:'\e09f'}.fi-move:before{content:'\e0a0'}.fi-musical-note:before{content:'\e0a1'}.fi-paperclip:before{content:'\e0a2'}.fi-pencil:before{content:'\e0a3'}.fi-people:before{content:'\e0a4'}.fi-person:before{content:'\e0a5'}.fi-phone:before{content:'\e0a6'}.fi-pie-chart:before{content:'\e0a7'}.fi-pin:before{content:'\e0a8'}.fi-play-circle:before{content:'\e0a9'}.fi-plus:before{content:'\e0aa'}.fi-power-standby:before{content:'\e0ab'}.fi-print:before{content:'\e0ac'}.fi-project:before{content:'\e0ad'}.fi-pulse:before{content:'\e0ae'}.fi-puzzle-piece:before{content:'\e0af'}.fi-question-mark:before{content:'\e0b0'}.fi-rain:before{content:'\e0b1'}.fi-random:before{content:'\e0b2'}.fi-reload:before{content:'\e0b3'}.fi-resize-both:before{content:'\e0b4'}.fi-resize-height:before{content:'\e0b5'}.fi-resize-width:before{content:'\e0b6'}.fi-rss-alt:before{content:'\e0b7'}.fi-rss:before{content:'\e0b8'}.fi-script:before{content:'\e0b9'}.fi-share-boxed:before{content:'\e0ba'}.fi-share:before{content:'\e0bb'}.fi-shield:before{content:'\e0bc'}.fi-signal:before{content:'\e0bd'}.fi-signpost:before{content:'\e0be'}.fi-sort-ascending:before{content:'\e0bf'}.fi-sort-descending:before{content:'\e0c0'}.fi-spreadsheet:before{content:'\e0c1'}.fi-star:before{content:'\e0c2'}.fi-sun:before{content:'\e0c3'}.fi-tablet:before{content:'\e0c4'}.fi-tag:before{content:'\e0c5'}.fi-tags:before{content:'\e0c6'}.fi-target:before{content:'\e0c7'}.fi-task:before{content:'\e0c8'}.fi-terminal:before{content:'\e0c9'}.fi-text:before{content:'\e0ca'}.fi-thumb-down:before{content:'\e0cb'}.fi-thumb-up:before{content:'\e0cc'}.fi-timer:before{content:'\e0cd'}.fi-transfer:before{content:'\e0ce'}.fi-trash:before{content:'\e0cf'}.fi-underline:before{content:'\e0d0'}.fi-vertical-align-bottom:before{content:'\e0d1'}.fi-vertical-align-center:before{content:'\e0d2'}.fi-vertical-align-top:before{content:'\e0d3'}.fi-video:before{content:'\e0d4'}.fi-volume-high:before{content:'\e0d5'}.fi-volume-low:before{content:'\e0d6'}.fi-volume-off:before{content:'\e0d7'}.fi-warning:before{content:'\e0d8'}.fi-wifi:before{content:'\e0d9'}.fi-wrench:before{content:'\e0da'}.fi-x:before{content:'\e0db'}.fi-yen:before{content:'\e0dc'}.fi-zoom-in:before{content:'\e0dd'}.fi-zoom-out:before{content:'\e0de'} \ No newline at end of file diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.scss b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.scss new file mode 100644 index 00000000..fe471389 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.scss @@ -0,0 +1,1398 @@ +/* Foundation */ + +/* Font path variable */ +$icon-font-path: '../fonts/' !default; + +@font-face { + font-family: 'Icons'; + src: url('#{$icon-font-path}open-iconic.eot'); + src: url('#{$icon-font-path}open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('#{$icon-font-path}open-iconic.woff') format('woff'), url('#{$icon-font-path}open-iconic.ttf') format('truetype'), url('#{$icon-font-path}open-iconic.otf') format('opentype'), url('#{$icon-font-path}open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + + +.fi-account-login:before, + +.fi-account-logout:before, + +.fi-action-redo:before, + +.fi-action-undo:before, + +.fi-align-center:before, + +.fi-align-left:before, + +.fi-align-right:before, + +.fi-aperture:before, + +.fi-arrow-bottom:before, + +.fi-arrow-circle-bottom:before, + +.fi-arrow-circle-left:before, + +.fi-arrow-circle-right:before, + +.fi-arrow-circle-top:before, + +.fi-arrow-left:before, + +.fi-arrow-right:before, + +.fi-arrow-thick-bottom:before, + +.fi-arrow-thick-left:before, + +.fi-arrow-thick-right:before, + +.fi-arrow-thick-top:before, + +.fi-arrow-top:before, + +.fi-audio-spectrum:before, + +.fi-audio:before, + +.fi-badge:before, + +.fi-ban:before, + +.fi-bar-chart:before, + +.fi-basket:before, + +.fi-battery-empty:before, + +.fi-battery-full:before, + +.fi-beaker:before, + +.fi-bell:before, + +.fi-bluetooth:before, + +.fi-bold:before, + +.fi-bolt:before, + +.fi-book:before, + +.fi-bookmark:before, + +.fi-box:before, + +.fi-briefcase:before, + +.fi-british-pound:before, + +.fi-browser:before, + +.fi-brush:before, + +.fi-bug:before, + +.fi-bullhorn:before, + +.fi-calculator:before, + +.fi-calendar:before, + +.fi-camera-slr:before, + +.fi-caret-bottom:before, + +.fi-caret-left:before, + +.fi-caret-right:before, + +.fi-caret-top:before, + +.fi-cart:before, + +.fi-chat:before, + +.fi-check:before, + +.fi-chevron-bottom:before, + +.fi-chevron-left:before, + +.fi-chevron-right:before, + +.fi-chevron-top:before, + +.fi-circle-check:before, + +.fi-circle-x:before, + +.fi-clipboard:before, + +.fi-clock:before, + +.fi-cloud-download:before, + +.fi-cloud-upload:before, + +.fi-cloud:before, + +.fi-cloudy:before, + +.fi-code:before, + +.fi-cog:before, + +.fi-collapse-down:before, + +.fi-collapse-left:before, + +.fi-collapse-right:before, + +.fi-collapse-up:before, + +.fi-command:before, + +.fi-comment-square:before, + +.fi-compass:before, + +.fi-contrast:before, + +.fi-copywriting:before, + +.fi-credit-card:before, + +.fi-crop:before, + +.fi-dashboard:before, + +.fi-data-transfer-download:before, + +.fi-data-transfer-upload:before, + +.fi-delete:before, + +.fi-dial:before, + +.fi-document:before, + +.fi-dollar:before, + +.fi-double-quote-sans-left:before, + +.fi-double-quote-sans-right:before, + +.fi-double-quote-serif-left:before, + +.fi-double-quote-serif-right:before, + +.fi-droplet:before, + +.fi-eject:before, + +.fi-elevator:before, + +.fi-ellipses:before, + +.fi-envelope-closed:before, + +.fi-envelope-open:before, + +.fi-euro:before, + +.fi-excerpt:before, + +.fi-expand-down:before, + +.fi-expand-left:before, + +.fi-expand-right:before, + +.fi-expand-up:before, + +.fi-external-link:before, + +.fi-eye:before, + +.fi-eyedropper:before, + +.fi-file:before, + +.fi-fire:before, + +.fi-flag:before, + +.fi-flash:before, + +.fi-folder:before, + +.fi-fork:before, + +.fi-fullscreen-enter:before, + +.fi-fullscreen-exit:before, + +.fi-globe:before, + +.fi-graph:before, + +.fi-grid-four-up:before, + +.fi-grid-three-up:before, + +.fi-grid-two-up:before, + +.fi-hard-drive:before, + +.fi-header:before, + +.fi-headphones:before, + +.fi-heart:before, + +.fi-home:before, + +.fi-image:before, + +.fi-inbox:before, + +.fi-infinity:before, + +.fi-info:before, + +.fi-italic:before, + +.fi-justify-center:before, + +.fi-justify-left:before, + +.fi-justify-right:before, + +.fi-key:before, + +.fi-laptop:before, + +.fi-layers:before, + +.fi-lightbulb:before, + +.fi-link-broken:before, + +.fi-link-intact:before, + +.fi-list-rich:before, + +.fi-list:before, + +.fi-location:before, + +.fi-lock-locked:before, + +.fi-lock-unlocked:before, + +.fi-loop-circular:before, + +.fi-loop-square:before, + +.fi-loop:before, + +.fi-magnifying-glass:before, + +.fi-map-marker:before, + +.fi-map:before, + +.fi-media-pause:before, + +.fi-media-play:before, + +.fi-media-record:before, + +.fi-media-skip-backward:before, + +.fi-media-skip-forward:before, + +.fi-media-step-backward:before, + +.fi-media-step-forward:before, + +.fi-media-stop:before, + +.fi-medical-cross:before, + +.fi-menu:before, + +.fi-microphone:before, + +.fi-minus:before, + +.fi-monitor:before, + +.fi-moon:before, + +.fi-move:before, + +.fi-musical-note:before, + +.fi-paperclip:before, + +.fi-pencil:before, + +.fi-people:before, + +.fi-person:before, + +.fi-phone:before, + +.fi-pie-chart:before, + +.fi-pin:before, + +.fi-play-circle:before, + +.fi-plus:before, + +.fi-power-standby:before, + +.fi-print:before, + +.fi-project:before, + +.fi-pulse:before, + +.fi-puzzle-piece:before, + +.fi-question-mark:before, + +.fi-rain:before, + +.fi-random:before, + +.fi-reload:before, + +.fi-resize-both:before, + +.fi-resize-height:before, + +.fi-resize-width:before, + +.fi-rss-alt:before, + +.fi-rss:before, + +.fi-script:before, + +.fi-share-boxed:before, + +.fi-share:before, + +.fi-shield:before, + +.fi-signal:before, + +.fi-signpost:before, + +.fi-sort-ascending:before, + +.fi-sort-descending:before, + +.fi-spreadsheet:before, + +.fi-star:before, + +.fi-sun:before, + +.fi-tablet:before, + +.fi-tag:before, + +.fi-tags:before, + +.fi-target:before, + +.fi-task:before, + +.fi-terminal:before, + +.fi-text:before, + +.fi-thumb-down:before, + +.fi-thumb-up:before, + +.fi-timer:before, + +.fi-transfer:before, + +.fi-trash:before, + +.fi-underline:before, + +.fi-vertical-align-bottom:before, + +.fi-vertical-align-center:before, + +.fi-vertical-align-top:before, + +.fi-video:before, + +.fi-volume-high:before, + +.fi-volume-low:before, + +.fi-volume-off:before, + +.fi-warning:before, + +.fi-wifi:before, + +.fi-wrench:before, + +.fi-x:before, + +.fi-yen:before, + +.fi-zoom-in:before, + +.fi-zoom-out:before + { + font-family: 'Icons'; + font-style: normal; + font-weight: normal; + font-variant: normal; + text-transform: none; + line-height: 1; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + display: inline-block; + text-decoration: inherit; +} + + +[class*='fi-'].oi-align-center:before { + text-align: center; +} + +[class*='fi-'].oi-align-left:before { + text-align: left; +} + +[class*='fi-'].oi-align-right:before { + text-align: right; +} + + +[class*='fi-'].oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} + +[class*='fi-'].oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); +} + +[class*='fi-'].oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); +} + + + +.fi-account-login:before { + content:'\e000'; +} + +.fi-account-logout:before { + content:'\e001'; +} + +.fi-action-redo:before { + content:'\e002'; +} + +.fi-action-undo:before { + content:'\e003'; +} + +.fi-align-center:before { + content:'\e004'; +} + +.fi-align-left:before { + content:'\e005'; +} + +.fi-align-right:before { + content:'\e006'; +} + +.fi-aperture:before { + content:'\e007'; +} + +.fi-arrow-bottom:before { + content:'\e008'; +} + +.fi-arrow-circle-bottom:before { + content:'\e009'; +} + +.fi-arrow-circle-left:before { + content:'\e00a'; +} + +.fi-arrow-circle-right:before { + content:'\e00b'; +} + +.fi-arrow-circle-top:before { + content:'\e00c'; +} + +.fi-arrow-left:before { + content:'\e00d'; +} + +.fi-arrow-right:before { + content:'\e00e'; +} + +.fi-arrow-thick-bottom:before { + content:'\e00f'; +} + +.fi-arrow-thick-left:before { + content:'\e010'; +} + +.fi-arrow-thick-right:before { + content:'\e011'; +} + +.fi-arrow-thick-top:before { + content:'\e012'; +} + +.fi-arrow-top:before { + content:'\e013'; +} + +.fi-audio-spectrum:before { + content:'\e014'; +} + +.fi-audio:before { + content:'\e015'; +} + +.fi-badge:before { + content:'\e016'; +} + +.fi-ban:before { + content:'\e017'; +} + +.fi-bar-chart:before { + content:'\e018'; +} + +.fi-basket:before { + content:'\e019'; +} + +.fi-battery-empty:before { + content:'\e01a'; +} + +.fi-battery-full:before { + content:'\e01b'; +} + +.fi-beaker:before { + content:'\e01c'; +} + +.fi-bell:before { + content:'\e01d'; +} + +.fi-bluetooth:before { + content:'\e01e'; +} + +.fi-bold:before { + content:'\e01f'; +} + +.fi-bolt:before { + content:'\e020'; +} + +.fi-book:before { + content:'\e021'; +} + +.fi-bookmark:before { + content:'\e022'; +} + +.fi-box:before { + content:'\e023'; +} + +.fi-briefcase:before { + content:'\e024'; +} + +.fi-british-pound:before { + content:'\e025'; +} + +.fi-browser:before { + content:'\e026'; +} + +.fi-brush:before { + content:'\e027'; +} + +.fi-bug:before { + content:'\e028'; +} + +.fi-bullhorn:before { + content:'\e029'; +} + +.fi-calculator:before { + content:'\e02a'; +} + +.fi-calendar:before { + content:'\e02b'; +} + +.fi-camera-slr:before { + content:'\e02c'; +} + +.fi-caret-bottom:before { + content:'\e02d'; +} + +.fi-caret-left:before { + content:'\e02e'; +} + +.fi-caret-right:before { + content:'\e02f'; +} + +.fi-caret-top:before { + content:'\e030'; +} + +.fi-cart:before { + content:'\e031'; +} + +.fi-chat:before { + content:'\e032'; +} + +.fi-check:before { + content:'\e033'; +} + +.fi-chevron-bottom:before { + content:'\e034'; +} + +.fi-chevron-left:before { + content:'\e035'; +} + +.fi-chevron-right:before { + content:'\e036'; +} + +.fi-chevron-top:before { + content:'\e037'; +} + +.fi-circle-check:before { + content:'\e038'; +} + +.fi-circle-x:before { + content:'\e039'; +} + +.fi-clipboard:before { + content:'\e03a'; +} + +.fi-clock:before { + content:'\e03b'; +} + +.fi-cloud-download:before { + content:'\e03c'; +} + +.fi-cloud-upload:before { + content:'\e03d'; +} + +.fi-cloud:before { + content:'\e03e'; +} + +.fi-cloudy:before { + content:'\e03f'; +} + +.fi-code:before { + content:'\e040'; +} + +.fi-cog:before { + content:'\e041'; +} + +.fi-collapse-down:before { + content:'\e042'; +} + +.fi-collapse-left:before { + content:'\e043'; +} + +.fi-collapse-right:before { + content:'\e044'; +} + +.fi-collapse-up:before { + content:'\e045'; +} + +.fi-command:before { + content:'\e046'; +} + +.fi-comment-square:before { + content:'\e047'; +} + +.fi-compass:before { + content:'\e048'; +} + +.fi-contrast:before { + content:'\e049'; +} + +.fi-copywriting:before { + content:'\e04a'; +} + +.fi-credit-card:before { + content:'\e04b'; +} + +.fi-crop:before { + content:'\e04c'; +} + +.fi-dashboard:before { + content:'\e04d'; +} + +.fi-data-transfer-download:before { + content:'\e04e'; +} + +.fi-data-transfer-upload:before { + content:'\e04f'; +} + +.fi-delete:before { + content:'\e050'; +} + +.fi-dial:before { + content:'\e051'; +} + +.fi-document:before { + content:'\e052'; +} + +.fi-dollar:before { + content:'\e053'; +} + +.fi-double-quote-sans-left:before { + content:'\e054'; +} + +.fi-double-quote-sans-right:before { + content:'\e055'; +} + +.fi-double-quote-serif-left:before { + content:'\e056'; +} + +.fi-double-quote-serif-right:before { + content:'\e057'; +} + +.fi-droplet:before { + content:'\e058'; +} + +.fi-eject:before { + content:'\e059'; +} + +.fi-elevator:before { + content:'\e05a'; +} + +.fi-ellipses:before { + content:'\e05b'; +} + +.fi-envelope-closed:before { + content:'\e05c'; +} + +.fi-envelope-open:before { + content:'\e05d'; +} + +.fi-euro:before { + content:'\e05e'; +} + +.fi-excerpt:before { + content:'\e05f'; +} + +.fi-expand-down:before { + content:'\e060'; +} + +.fi-expand-left:before { + content:'\e061'; +} + +.fi-expand-right:before { + content:'\e062'; +} + +.fi-expand-up:before { + content:'\e063'; +} + +.fi-external-link:before { + content:'\e064'; +} + +.fi-eye:before { + content:'\e065'; +} + +.fi-eyedropper:before { + content:'\e066'; +} + +.fi-file:before { + content:'\e067'; +} + +.fi-fire:before { + content:'\e068'; +} + +.fi-flag:before { + content:'\e069'; +} + +.fi-flash:before { + content:'\e06a'; +} + +.fi-folder:before { + content:'\e06b'; +} + +.fi-fork:before { + content:'\e06c'; +} + +.fi-fullscreen-enter:before { + content:'\e06d'; +} + +.fi-fullscreen-exit:before { + content:'\e06e'; +} + +.fi-globe:before { + content:'\e06f'; +} + +.fi-graph:before { + content:'\e070'; +} + +.fi-grid-four-up:before { + content:'\e071'; +} + +.fi-grid-three-up:before { + content:'\e072'; +} + +.fi-grid-two-up:before { + content:'\e073'; +} + +.fi-hard-drive:before { + content:'\e074'; +} + +.fi-header:before { + content:'\e075'; +} + +.fi-headphones:before { + content:'\e076'; +} + +.fi-heart:before { + content:'\e077'; +} + +.fi-home:before { + content:'\e078'; +} + +.fi-image:before { + content:'\e079'; +} + +.fi-inbox:before { + content:'\e07a'; +} + +.fi-infinity:before { + content:'\e07b'; +} + +.fi-info:before { + content:'\e07c'; +} + +.fi-italic:before { + content:'\e07d'; +} + +.fi-justify-center:before { + content:'\e07e'; +} + +.fi-justify-left:before { + content:'\e07f'; +} + +.fi-justify-right:before { + content:'\e080'; +} + +.fi-key:before { + content:'\e081'; +} + +.fi-laptop:before { + content:'\e082'; +} + +.fi-layers:before { + content:'\e083'; +} + +.fi-lightbulb:before { + content:'\e084'; +} + +.fi-link-broken:before { + content:'\e085'; +} + +.fi-link-intact:before { + content:'\e086'; +} + +.fi-list-rich:before { + content:'\e087'; +} + +.fi-list:before { + content:'\e088'; +} + +.fi-location:before { + content:'\e089'; +} + +.fi-lock-locked:before { + content:'\e08a'; +} + +.fi-lock-unlocked:before { + content:'\e08b'; +} + +.fi-loop-circular:before { + content:'\e08c'; +} + +.fi-loop-square:before { + content:'\e08d'; +} + +.fi-loop:before { + content:'\e08e'; +} + +.fi-magnifying-glass:before { + content:'\e08f'; +} + +.fi-map-marker:before { + content:'\e090'; +} + +.fi-map:before { + content:'\e091'; +} + +.fi-media-pause:before { + content:'\e092'; +} + +.fi-media-play:before { + content:'\e093'; +} + +.fi-media-record:before { + content:'\e094'; +} + +.fi-media-skip-backward:before { + content:'\e095'; +} + +.fi-media-skip-forward:before { + content:'\e096'; +} + +.fi-media-step-backward:before { + content:'\e097'; +} + +.fi-media-step-forward:before { + content:'\e098'; +} + +.fi-media-stop:before { + content:'\e099'; +} + +.fi-medical-cross:before { + content:'\e09a'; +} + +.fi-menu:before { + content:'\e09b'; +} + +.fi-microphone:before { + content:'\e09c'; +} + +.fi-minus:before { + content:'\e09d'; +} + +.fi-monitor:before { + content:'\e09e'; +} + +.fi-moon:before { + content:'\e09f'; +} + +.fi-move:before { + content:'\e0a0'; +} + +.fi-musical-note:before { + content:'\e0a1'; +} + +.fi-paperclip:before { + content:'\e0a2'; +} + +.fi-pencil:before { + content:'\e0a3'; +} + +.fi-people:before { + content:'\e0a4'; +} + +.fi-person:before { + content:'\e0a5'; +} + +.fi-phone:before { + content:'\e0a6'; +} + +.fi-pie-chart:before { + content:'\e0a7'; +} + +.fi-pin:before { + content:'\e0a8'; +} + +.fi-play-circle:before { + content:'\e0a9'; +} + +.fi-plus:before { + content:'\e0aa'; +} + +.fi-power-standby:before { + content:'\e0ab'; +} + +.fi-print:before { + content:'\e0ac'; +} + +.fi-project:before { + content:'\e0ad'; +} + +.fi-pulse:before { + content:'\e0ae'; +} + +.fi-puzzle-piece:before { + content:'\e0af'; +} + +.fi-question-mark:before { + content:'\e0b0'; +} + +.fi-rain:before { + content:'\e0b1'; +} + +.fi-random:before { + content:'\e0b2'; +} + +.fi-reload:before { + content:'\e0b3'; +} + +.fi-resize-both:before { + content:'\e0b4'; +} + +.fi-resize-height:before { + content:'\e0b5'; +} + +.fi-resize-width:before { + content:'\e0b6'; +} + +.fi-rss-alt:before { + content:'\e0b7'; +} + +.fi-rss:before { + content:'\e0b8'; +} + +.fi-script:before { + content:'\e0b9'; +} + +.fi-share-boxed:before { + content:'\e0ba'; +} + +.fi-share:before { + content:'\e0bb'; +} + +.fi-shield:before { + content:'\e0bc'; +} + +.fi-signal:before { + content:'\e0bd'; +} + +.fi-signpost:before { + content:'\e0be'; +} + +.fi-sort-ascending:before { + content:'\e0bf'; +} + +.fi-sort-descending:before { + content:'\e0c0'; +} + +.fi-spreadsheet:before { + content:'\e0c1'; +} + +.fi-star:before { + content:'\e0c2'; +} + +.fi-sun:before { + content:'\e0c3'; +} + +.fi-tablet:before { + content:'\e0c4'; +} + +.fi-tag:before { + content:'\e0c5'; +} + +.fi-tags:before { + content:'\e0c6'; +} + +.fi-target:before { + content:'\e0c7'; +} + +.fi-task:before { + content:'\e0c8'; +} + +.fi-terminal:before { + content:'\e0c9'; +} + +.fi-text:before { + content:'\e0ca'; +} + +.fi-thumb-down:before { + content:'\e0cb'; +} + +.fi-thumb-up:before { + content:'\e0cc'; +} + +.fi-timer:before { + content:'\e0cd'; +} + +.fi-transfer:before { + content:'\e0ce'; +} + +.fi-trash:before { + content:'\e0cf'; +} + +.fi-underline:before { + content:'\e0d0'; +} + +.fi-vertical-align-bottom:before { + content:'\e0d1'; +} + +.fi-vertical-align-center:before { + content:'\e0d2'; +} + +.fi-vertical-align-top:before { + content:'\e0d3'; +} + +.fi-video:before { + content:'\e0d4'; +} + +.fi-volume-high:before { + content:'\e0d5'; +} + +.fi-volume-low:before { + content:'\e0d6'; +} + +.fi-volume-off:before { + content:'\e0d7'; +} + +.fi-warning:before { + content:'\e0d8'; +} + +.fi-wifi:before { + content:'\e0d9'; +} + +.fi-wrench:before { + content:'\e0da'; +} + +.fi-x:before { + content:'\e0db'; +} + +.fi-yen:before { + content:'\e0dc'; +} + +.fi-zoom-in:before { + content:'\e0dd'; +} + +.fi-zoom-out:before { + content:'\e0de'; +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.styl b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.styl new file mode 100644 index 00000000..a52637ab --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic-foundation.styl @@ -0,0 +1,1392 @@ +/* Foundation */ + +@font-face + font-family 'Icons' + src url('../fonts/open-iconic.eot') + src url('../fonts/open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('../fonts/open-iconic.woff') format('woff'), url('../fonts/open-iconic.ttf') format('truetype'), url('../fonts/open-iconic.otf') format('opentype'), url('../fonts/open-iconic.svg#iconic-sm') format('svg') + font-weight normal + font-style normal + + + +.fi-account-loginbefore, + +.fi-account-logoutbefore, + +.fi-action-redobefore, + +.fi-action-undobefore, + +.fi-align-centerbefore, + +.fi-align-leftbefore, + +.fi-align-rightbefore, + +.fi-aperturebefore, + +.fi-arrow-bottombefore, + +.fi-arrow-circle-bottombefore, + +.fi-arrow-circle-leftbefore, + +.fi-arrow-circle-rightbefore, + +.fi-arrow-circle-topbefore, + +.fi-arrow-leftbefore, + +.fi-arrow-rightbefore, + +.fi-arrow-thick-bottombefore, + +.fi-arrow-thick-leftbefore, + +.fi-arrow-thick-rightbefore, + +.fi-arrow-thick-topbefore, + +.fi-arrow-topbefore, + +.fi-audio-spectrumbefore, + +.fi-audiobefore, + +.fi-badgebefore, + +.fi-banbefore, + +.fi-bar-chartbefore, + +.fi-basketbefore, + +.fi-battery-emptybefore, + +.fi-battery-fullbefore, + +.fi-beakerbefore, + +.fi-bellbefore, + +.fi-bluetoothbefore, + +.fi-boldbefore, + +.fi-boltbefore, + +.fi-bookbefore, + +.fi-bookmarkbefore, + +.fi-boxbefore, + +.fi-briefcasebefore, + +.fi-british-poundbefore, + +.fi-browserbefore, + +.fi-brushbefore, + +.fi-bugbefore, + +.fi-bullhornbefore, + +.fi-calculatorbefore, + +.fi-calendarbefore, + +.fi-camera-slrbefore, + +.fi-caret-bottombefore, + +.fi-caret-leftbefore, + +.fi-caret-rightbefore, + +.fi-caret-topbefore, + +.fi-cartbefore, + +.fi-chatbefore, + +.fi-checkbefore, + +.fi-chevron-bottombefore, + +.fi-chevron-leftbefore, + +.fi-chevron-rightbefore, + +.fi-chevron-topbefore, + +.fi-circle-checkbefore, + +.fi-circle-xbefore, + +.fi-clipboardbefore, + +.fi-clockbefore, + +.fi-cloud-downloadbefore, + +.fi-cloud-uploadbefore, + +.fi-cloudbefore, + +.fi-cloudybefore, + +.fi-codebefore, + +.fi-cogbefore, + +.fi-collapse-downbefore, + +.fi-collapse-leftbefore, + +.fi-collapse-rightbefore, + +.fi-collapse-upbefore, + +.fi-commandbefore, + +.fi-comment-squarebefore, + +.fi-compassbefore, + +.fi-contrastbefore, + +.fi-copywritingbefore, + +.fi-credit-cardbefore, + +.fi-cropbefore, + +.fi-dashboardbefore, + +.fi-data-transfer-downloadbefore, + +.fi-data-transfer-uploadbefore, + +.fi-deletebefore, + +.fi-dialbefore, + +.fi-documentbefore, + +.fi-dollarbefore, + +.fi-double-quote-sans-leftbefore, + +.fi-double-quote-sans-rightbefore, + +.fi-double-quote-serif-leftbefore, + +.fi-double-quote-serif-rightbefore, + +.fi-dropletbefore, + +.fi-ejectbefore, + +.fi-elevatorbefore, + +.fi-ellipsesbefore, + +.fi-envelope-closedbefore, + +.fi-envelope-openbefore, + +.fi-eurobefore, + +.fi-excerptbefore, + +.fi-expand-downbefore, + +.fi-expand-leftbefore, + +.fi-expand-rightbefore, + +.fi-expand-upbefore, + +.fi-external-linkbefore, + +.fi-eyebefore, + +.fi-eyedropperbefore, + +.fi-filebefore, + +.fi-firebefore, + +.fi-flagbefore, + +.fi-flashbefore, + +.fi-folderbefore, + +.fi-forkbefore, + +.fi-fullscreen-enterbefore, + +.fi-fullscreen-exitbefore, + +.fi-globebefore, + +.fi-graphbefore, + +.fi-grid-four-upbefore, + +.fi-grid-three-upbefore, + +.fi-grid-two-upbefore, + +.fi-hard-drivebefore, + +.fi-headerbefore, + +.fi-headphonesbefore, + +.fi-heartbefore, + +.fi-homebefore, + +.fi-imagebefore, + +.fi-inboxbefore, + +.fi-infinitybefore, + +.fi-infobefore, + +.fi-italicbefore, + +.fi-justify-centerbefore, + +.fi-justify-leftbefore, + +.fi-justify-rightbefore, + +.fi-keybefore, + +.fi-laptopbefore, + +.fi-layersbefore, + +.fi-lightbulbbefore, + +.fi-link-brokenbefore, + +.fi-link-intactbefore, + +.fi-list-richbefore, + +.fi-listbefore, + +.fi-locationbefore, + +.fi-lock-lockedbefore, + +.fi-lock-unlockedbefore, + +.fi-loop-circularbefore, + +.fi-loop-squarebefore, + +.fi-loopbefore, + +.fi-magnifying-glassbefore, + +.fi-map-markerbefore, + +.fi-mapbefore, + +.fi-media-pausebefore, + +.fi-media-playbefore, + +.fi-media-recordbefore, + +.fi-media-skip-backwardbefore, + +.fi-media-skip-forwardbefore, + +.fi-media-step-backwardbefore, + +.fi-media-step-forwardbefore, + +.fi-media-stopbefore, + +.fi-medical-crossbefore, + +.fi-menubefore, + +.fi-microphonebefore, + +.fi-minusbefore, + +.fi-monitorbefore, + +.fi-moonbefore, + +.fi-movebefore, + +.fi-musical-notebefore, + +.fi-paperclipbefore, + +.fi-pencilbefore, + +.fi-peoplebefore, + +.fi-personbefore, + +.fi-phonebefore, + +.fi-pie-chartbefore, + +.fi-pinbefore, + +.fi-play-circlebefore, + +.fi-plusbefore, + +.fi-power-standbybefore, + +.fi-printbefore, + +.fi-projectbefore, + +.fi-pulsebefore, + +.fi-puzzle-piecebefore, + +.fi-question-markbefore, + +.fi-rainbefore, + +.fi-randombefore, + +.fi-reloadbefore, + +.fi-resize-bothbefore, + +.fi-resize-heightbefore, + +.fi-resize-widthbefore, + +.fi-rss-altbefore, + +.fi-rssbefore, + +.fi-scriptbefore, + +.fi-share-boxedbefore, + +.fi-sharebefore, + +.fi-shieldbefore, + +.fi-signalbefore, + +.fi-signpostbefore, + +.fi-sort-ascendingbefore, + +.fi-sort-descendingbefore, + +.fi-spreadsheetbefore, + +.fi-starbefore, + +.fi-sunbefore, + +.fi-tabletbefore, + +.fi-tagbefore, + +.fi-tagsbefore, + +.fi-targetbefore, + +.fi-taskbefore, + +.fi-terminalbefore, + +.fi-textbefore, + +.fi-thumb-downbefore, + +.fi-thumb-upbefore, + +.fi-timerbefore, + +.fi-transferbefore, + +.fi-trashbefore, + +.fi-underlinebefore, + +.fi-vertical-align-bottombefore, + +.fi-vertical-align-centerbefore, + +.fi-vertical-align-topbefore, + +.fi-videobefore, + +.fi-volume-highbefore, + +.fi-volume-lowbefore, + +.fi-volume-offbefore, + +.fi-warningbefore, + +.fi-wifibefore, + +.fi-wrenchbefore, + +.fi-xbefore, + +.fi-yenbefore, + +.fi-zoom-inbefore, + +.fi-zoom-outbefore + + font-family 'Icons' + font-style normal + font-weight normal + font-variant normal + text-transform none + line-height 1 + -webkit-font-smoothing antialiased + -moz-osx-font-smoothing grayscale + display inline-block + text-decoration inherit + + +[class*='fi-'].oi-align-center:before + text-align center + + +[class*='fi-'].oi-align-left:before + text-align left + + +[class*='fi-'].oi-align-right:before + text-align right + + + +[class*='fi-'].oi-flip-horizontal:before + -webkit-transform scale(-1, 1) + -ms-transform scale(-1, 1) + transform scale(-1, 1) + + +[class*='fi-'].oi-flip-vertical:before + -webkit-transform scale(1, -1) + -ms-transform scale(-1, 1) + transform scale(1, -1) + + +[class*='fi-'].oi-flip-horizontal-vertical:before + -webkit-transform scale(-1, -1) + -ms-transform scale(-1, 1) + transform scale(-1, -1) + + +.fi-account-login:before + content'\e000' + + +.fi-account-logout:before + content'\e001' + + +.fi-action-redo:before + content'\e002' + + +.fi-action-undo:before + content'\e003' + + +.fi-align-center:before + content'\e004' + + +.fi-align-left:before + content'\e005' + + +.fi-align-right:before + content'\e006' + + +.fi-aperture:before + content'\e007' + + +.fi-arrow-bottom:before + content'\e008' + + +.fi-arrow-circle-bottom:before + content'\e009' + + +.fi-arrow-circle-left:before + content'\e00a' + + +.fi-arrow-circle-right:before + content'\e00b' + + +.fi-arrow-circle-top:before + content'\e00c' + + +.fi-arrow-left:before + content'\e00d' + + +.fi-arrow-right:before + content'\e00e' + + +.fi-arrow-thick-bottom:before + content'\e00f' + + +.fi-arrow-thick-left:before + content'\e010' + + +.fi-arrow-thick-right:before + content'\e011' + + +.fi-arrow-thick-top:before + content'\e012' + + +.fi-arrow-top:before + content'\e013' + + +.fi-audio-spectrum:before + content'\e014' + + +.fi-audio:before + content'\e015' + + +.fi-badge:before + content'\e016' + + +.fi-ban:before + content'\e017' + + +.fi-bar-chart:before + content'\e018' + + +.fi-basket:before + content'\e019' + + +.fi-battery-empty:before + content'\e01a' + + +.fi-battery-full:before + content'\e01b' + + +.fi-beaker:before + content'\e01c' + + +.fi-bell:before + content'\e01d' + + +.fi-bluetooth:before + content'\e01e' + + +.fi-bold:before + content'\e01f' + + +.fi-bolt:before + content'\e020' + + +.fi-book:before + content'\e021' + + +.fi-bookmark:before + content'\e022' + + +.fi-box:before + content'\e023' + + +.fi-briefcase:before + content'\e024' + + +.fi-british-pound:before + content'\e025' + + +.fi-browser:before + content'\e026' + + +.fi-brush:before + content'\e027' + + +.fi-bug:before + content'\e028' + + +.fi-bullhorn:before + content'\e029' + + +.fi-calculator:before + content'\e02a' + + +.fi-calendar:before + content'\e02b' + + +.fi-camera-slr:before + content'\e02c' + + +.fi-caret-bottom:before + content'\e02d' + + +.fi-caret-left:before + content'\e02e' + + +.fi-caret-right:before + content'\e02f' + + +.fi-caret-top:before + content'\e030' + + +.fi-cart:before + content'\e031' + + +.fi-chat:before + content'\e032' + + +.fi-check:before + content'\e033' + + +.fi-chevron-bottom:before + content'\e034' + + +.fi-chevron-left:before + content'\e035' + + +.fi-chevron-right:before + content'\e036' + + +.fi-chevron-top:before + content'\e037' + + +.fi-circle-check:before + content'\e038' + + +.fi-circle-x:before + content'\e039' + + +.fi-clipboard:before + content'\e03a' + + +.fi-clock:before + content'\e03b' + + +.fi-cloud-download:before + content'\e03c' + + +.fi-cloud-upload:before + content'\e03d' + + +.fi-cloud:before + content'\e03e' + + +.fi-cloudy:before + content'\e03f' + + +.fi-code:before + content'\e040' + + +.fi-cog:before + content'\e041' + + +.fi-collapse-down:before + content'\e042' + + +.fi-collapse-left:before + content'\e043' + + +.fi-collapse-right:before + content'\e044' + + +.fi-collapse-up:before + content'\e045' + + +.fi-command:before + content'\e046' + + +.fi-comment-square:before + content'\e047' + + +.fi-compass:before + content'\e048' + + +.fi-contrast:before + content'\e049' + + +.fi-copywriting:before + content'\e04a' + + +.fi-credit-card:before + content'\e04b' + + +.fi-crop:before + content'\e04c' + + +.fi-dashboard:before + content'\e04d' + + +.fi-data-transfer-download:before + content'\e04e' + + +.fi-data-transfer-upload:before + content'\e04f' + + +.fi-delete:before + content'\e050' + + +.fi-dial:before + content'\e051' + + +.fi-document:before + content'\e052' + + +.fi-dollar:before + content'\e053' + + +.fi-double-quote-sans-left:before + content'\e054' + + +.fi-double-quote-sans-right:before + content'\e055' + + +.fi-double-quote-serif-left:before + content'\e056' + + +.fi-double-quote-serif-right:before + content'\e057' + + +.fi-droplet:before + content'\e058' + + +.fi-eject:before + content'\e059' + + +.fi-elevator:before + content'\e05a' + + +.fi-ellipses:before + content'\e05b' + + +.fi-envelope-closed:before + content'\e05c' + + +.fi-envelope-open:before + content'\e05d' + + +.fi-euro:before + content'\e05e' + + +.fi-excerpt:before + content'\e05f' + + +.fi-expand-down:before + content'\e060' + + +.fi-expand-left:before + content'\e061' + + +.fi-expand-right:before + content'\e062' + + +.fi-expand-up:before + content'\e063' + + +.fi-external-link:before + content'\e064' + + +.fi-eye:before + content'\e065' + + +.fi-eyedropper:before + content'\e066' + + +.fi-file:before + content'\e067' + + +.fi-fire:before + content'\e068' + + +.fi-flag:before + content'\e069' + + +.fi-flash:before + content'\e06a' + + +.fi-folder:before + content'\e06b' + + +.fi-fork:before + content'\e06c' + + +.fi-fullscreen-enter:before + content'\e06d' + + +.fi-fullscreen-exit:before + content'\e06e' + + +.fi-globe:before + content'\e06f' + + +.fi-graph:before + content'\e070' + + +.fi-grid-four-up:before + content'\e071' + + +.fi-grid-three-up:before + content'\e072' + + +.fi-grid-two-up:before + content'\e073' + + +.fi-hard-drive:before + content'\e074' + + +.fi-header:before + content'\e075' + + +.fi-headphones:before + content'\e076' + + +.fi-heart:before + content'\e077' + + +.fi-home:before + content'\e078' + + +.fi-image:before + content'\e079' + + +.fi-inbox:before + content'\e07a' + + +.fi-infinity:before + content'\e07b' + + +.fi-info:before + content'\e07c' + + +.fi-italic:before + content'\e07d' + + +.fi-justify-center:before + content'\e07e' + + +.fi-justify-left:before + content'\e07f' + + +.fi-justify-right:before + content'\e080' + + +.fi-key:before + content'\e081' + + +.fi-laptop:before + content'\e082' + + +.fi-layers:before + content'\e083' + + +.fi-lightbulb:before + content'\e084' + + +.fi-link-broken:before + content'\e085' + + +.fi-link-intact:before + content'\e086' + + +.fi-list-rich:before + content'\e087' + + +.fi-list:before + content'\e088' + + +.fi-location:before + content'\e089' + + +.fi-lock-locked:before + content'\e08a' + + +.fi-lock-unlocked:before + content'\e08b' + + +.fi-loop-circular:before + content'\e08c' + + +.fi-loop-square:before + content'\e08d' + + +.fi-loop:before + content'\e08e' + + +.fi-magnifying-glass:before + content'\e08f' + + +.fi-map-marker:before + content'\e090' + + +.fi-map:before + content'\e091' + + +.fi-media-pause:before + content'\e092' + + +.fi-media-play:before + content'\e093' + + +.fi-media-record:before + content'\e094' + + +.fi-media-skip-backward:before + content'\e095' + + +.fi-media-skip-forward:before + content'\e096' + + +.fi-media-step-backward:before + content'\e097' + + +.fi-media-step-forward:before + content'\e098' + + +.fi-media-stop:before + content'\e099' + + +.fi-medical-cross:before + content'\e09a' + + +.fi-menu:before + content'\e09b' + + +.fi-microphone:before + content'\e09c' + + +.fi-minus:before + content'\e09d' + + +.fi-monitor:before + content'\e09e' + + +.fi-moon:before + content'\e09f' + + +.fi-move:before + content'\e0a0' + + +.fi-musical-note:before + content'\e0a1' + + +.fi-paperclip:before + content'\e0a2' + + +.fi-pencil:before + content'\e0a3' + + +.fi-people:before + content'\e0a4' + + +.fi-person:before + content'\e0a5' + + +.fi-phone:before + content'\e0a6' + + +.fi-pie-chart:before + content'\e0a7' + + +.fi-pin:before + content'\e0a8' + + +.fi-play-circle:before + content'\e0a9' + + +.fi-plus:before + content'\e0aa' + + +.fi-power-standby:before + content'\e0ab' + + +.fi-print:before + content'\e0ac' + + +.fi-project:before + content'\e0ad' + + +.fi-pulse:before + content'\e0ae' + + +.fi-puzzle-piece:before + content'\e0af' + + +.fi-question-mark:before + content'\e0b0' + + +.fi-rain:before + content'\e0b1' + + +.fi-random:before + content'\e0b2' + + +.fi-reload:before + content'\e0b3' + + +.fi-resize-both:before + content'\e0b4' + + +.fi-resize-height:before + content'\e0b5' + + +.fi-resize-width:before + content'\e0b6' + + +.fi-rss-alt:before + content'\e0b7' + + +.fi-rss:before + content'\e0b8' + + +.fi-script:before + content'\e0b9' + + +.fi-share-boxed:before + content'\e0ba' + + +.fi-share:before + content'\e0bb' + + +.fi-shield:before + content'\e0bc' + + +.fi-signal:before + content'\e0bd' + + +.fi-signpost:before + content'\e0be' + + +.fi-sort-ascending:before + content'\e0bf' + + +.fi-sort-descending:before + content'\e0c0' + + +.fi-spreadsheet:before + content'\e0c1' + + +.fi-star:before + content'\e0c2' + + +.fi-sun:before + content'\e0c3' + + +.fi-tablet:before + content'\e0c4' + + +.fi-tag:before + content'\e0c5' + + +.fi-tags:before + content'\e0c6' + + +.fi-target:before + content'\e0c7' + + +.fi-task:before + content'\e0c8' + + +.fi-terminal:before + content'\e0c9' + + +.fi-text:before + content'\e0ca' + + +.fi-thumb-down:before + content'\e0cb' + + +.fi-thumb-up:before + content'\e0cc' + + +.fi-timer:before + content'\e0cd' + + +.fi-transfer:before + content'\e0ce' + + +.fi-trash:before + content'\e0cf' + + +.fi-underline:before + content'\e0d0' + + +.fi-vertical-align-bottom:before + content'\e0d1' + + +.fi-vertical-align-center:before + content'\e0d2' + + +.fi-vertical-align-top:before + content'\e0d3' + + +.fi-video:before + content'\e0d4' + + +.fi-volume-high:before + content'\e0d5' + + +.fi-volume-low:before + content'\e0d6' + + +.fi-volume-off:before + content'\e0d7' + + +.fi-warning:before + content'\e0d8' + + +.fi-wifi:before + content'\e0d9' + + +.fi-wrench:before + content'\e0da' + + +.fi-x:before + content'\e0db' + + +.fi-yen:before + content'\e0dc' + + +.fi-zoom-in:before + content'\e0dd' + + +.fi-zoom-out:before + content'\e0de' + + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.css b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.css new file mode 100644 index 00000000..301a138c --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.css @@ -0,0 +1,511 @@ + +@font-face { + font-family: 'Icons'; + src: url('../fonts/open-iconic.eot'); + src: url('../fonts/open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('../fonts/open-iconic.woff') format('woff'), url('../fonts/open-iconic.ttf') format('truetype'), url('../fonts/open-iconic.otf') format('opentype'), url('../fonts/open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + +.oi[data-glyph].oi-text-replace { + font-size: 0; + line-height: 0; +} + +.oi[data-glyph].oi-text-replace:before { + width: 1em; + text-align: center; +} + +.oi[data-glyph]:before { + font-family: 'Icons'; + display: inline-block; + speak: none; + line-height: 1; + vertical-align: baseline; + font-weight: normal; + font-style: normal; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} + +.oi[data-glyph]:empty:before { + width: 1em; + text-align: center; + box-sizing: content-box; +} + +.oi[data-glyph].oi-align-left:before { + text-align: left; +} + +.oi[data-glyph].oi-align-right:before { + text-align: right; +} + +.oi[data-glyph].oi-align-center:before { + text-align: center; +} + +.oi[data-glyph].oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); +} +.oi[data-glyph].oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); +} +.oi[data-glyph].oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); +} + + +.oi[data-glyph=account-login]:before { content:'\e000'; } + +.oi[data-glyph=account-logout]:before { content:'\e001'; } + +.oi[data-glyph=action-redo]:before { content:'\e002'; } + +.oi[data-glyph=action-undo]:before { content:'\e003'; } + +.oi[data-glyph=align-center]:before { content:'\e004'; } + +.oi[data-glyph=align-left]:before { content:'\e005'; } + +.oi[data-glyph=align-right]:before { content:'\e006'; } + +.oi[data-glyph=aperture]:before { content:'\e007'; } + +.oi[data-glyph=arrow-bottom]:before { content:'\e008'; } + +.oi[data-glyph=arrow-circle-bottom]:before { content:'\e009'; } + +.oi[data-glyph=arrow-circle-left]:before { content:'\e00a'; } + +.oi[data-glyph=arrow-circle-right]:before { content:'\e00b'; } + +.oi[data-glyph=arrow-circle-top]:before { content:'\e00c'; } + +.oi[data-glyph=arrow-left]:before { content:'\e00d'; } + +.oi[data-glyph=arrow-right]:before { content:'\e00e'; } + +.oi[data-glyph=arrow-thick-bottom]:before { content:'\e00f'; } + +.oi[data-glyph=arrow-thick-left]:before { content:'\e010'; } + +.oi[data-glyph=arrow-thick-right]:before { content:'\e011'; } + +.oi[data-glyph=arrow-thick-top]:before { content:'\e012'; } + +.oi[data-glyph=arrow-top]:before { content:'\e013'; } + +.oi[data-glyph=audio-spectrum]:before { content:'\e014'; } + +.oi[data-glyph=audio]:before { content:'\e015'; } + +.oi[data-glyph=badge]:before { content:'\e016'; } + +.oi[data-glyph=ban]:before { content:'\e017'; } + +.oi[data-glyph=bar-chart]:before { content:'\e018'; } + +.oi[data-glyph=basket]:before { content:'\e019'; } + +.oi[data-glyph=battery-empty]:before { content:'\e01a'; } + +.oi[data-glyph=battery-full]:before { content:'\e01b'; } + +.oi[data-glyph=beaker]:before { content:'\e01c'; } + +.oi[data-glyph=bell]:before { content:'\e01d'; } + +.oi[data-glyph=bluetooth]:before { content:'\e01e'; } + +.oi[data-glyph=bold]:before { content:'\e01f'; } + +.oi[data-glyph=bolt]:before { content:'\e020'; } + +.oi[data-glyph=book]:before { content:'\e021'; } + +.oi[data-glyph=bookmark]:before { content:'\e022'; } + +.oi[data-glyph=box]:before { content:'\e023'; } + +.oi[data-glyph=briefcase]:before { content:'\e024'; } + +.oi[data-glyph=british-pound]:before { content:'\e025'; } + +.oi[data-glyph=browser]:before { content:'\e026'; } + +.oi[data-glyph=brush]:before { content:'\e027'; } + +.oi[data-glyph=bug]:before { content:'\e028'; } + +.oi[data-glyph=bullhorn]:before { content:'\e029'; } + +.oi[data-glyph=calculator]:before { content:'\e02a'; } + +.oi[data-glyph=calendar]:before { content:'\e02b'; } + +.oi[data-glyph=camera-slr]:before { content:'\e02c'; } + +.oi[data-glyph=caret-bottom]:before { content:'\e02d'; } + +.oi[data-glyph=caret-left]:before { content:'\e02e'; } + +.oi[data-glyph=caret-right]:before { content:'\e02f'; } + +.oi[data-glyph=caret-top]:before { content:'\e030'; } + +.oi[data-glyph=cart]:before { content:'\e031'; } + +.oi[data-glyph=chat]:before { content:'\e032'; } + +.oi[data-glyph=check]:before { content:'\e033'; } + +.oi[data-glyph=chevron-bottom]:before { content:'\e034'; } + +.oi[data-glyph=chevron-left]:before { content:'\e035'; } + +.oi[data-glyph=chevron-right]:before { content:'\e036'; } + +.oi[data-glyph=chevron-top]:before { content:'\e037'; } + +.oi[data-glyph=circle-check]:before { content:'\e038'; } + +.oi[data-glyph=circle-x]:before { content:'\e039'; } + +.oi[data-glyph=clipboard]:before { content:'\e03a'; } + +.oi[data-glyph=clock]:before { content:'\e03b'; } + +.oi[data-glyph=cloud-download]:before { content:'\e03c'; } + +.oi[data-glyph=cloud-upload]:before { content:'\e03d'; } + +.oi[data-glyph=cloud]:before { content:'\e03e'; } + +.oi[data-glyph=cloudy]:before { content:'\e03f'; } + +.oi[data-glyph=code]:before { content:'\e040'; } + +.oi[data-glyph=cog]:before { content:'\e041'; } + +.oi[data-glyph=collapse-down]:before { content:'\e042'; } + +.oi[data-glyph=collapse-left]:before { content:'\e043'; } + +.oi[data-glyph=collapse-right]:before { content:'\e044'; } + +.oi[data-glyph=collapse-up]:before { content:'\e045'; } + +.oi[data-glyph=command]:before { content:'\e046'; } + +.oi[data-glyph=comment-square]:before { content:'\e047'; } + +.oi[data-glyph=compass]:before { content:'\e048'; } + +.oi[data-glyph=contrast]:before { content:'\e049'; } + +.oi[data-glyph=copywriting]:before { content:'\e04a'; } + +.oi[data-glyph=credit-card]:before { content:'\e04b'; } + +.oi[data-glyph=crop]:before { content:'\e04c'; } + +.oi[data-glyph=dashboard]:before { content:'\e04d'; } + +.oi[data-glyph=data-transfer-download]:before { content:'\e04e'; } + +.oi[data-glyph=data-transfer-upload]:before { content:'\e04f'; } + +.oi[data-glyph=delete]:before { content:'\e050'; } + +.oi[data-glyph=dial]:before { content:'\e051'; } + +.oi[data-glyph=document]:before { content:'\e052'; } + +.oi[data-glyph=dollar]:before { content:'\e053'; } + +.oi[data-glyph=double-quote-sans-left]:before { content:'\e054'; } + +.oi[data-glyph=double-quote-sans-right]:before { content:'\e055'; } + +.oi[data-glyph=double-quote-serif-left]:before { content:'\e056'; } + +.oi[data-glyph=double-quote-serif-right]:before { content:'\e057'; } + +.oi[data-glyph=droplet]:before { content:'\e058'; } + +.oi[data-glyph=eject]:before { content:'\e059'; } + +.oi[data-glyph=elevator]:before { content:'\e05a'; } + +.oi[data-glyph=ellipses]:before { content:'\e05b'; } + +.oi[data-glyph=envelope-closed]:before { content:'\e05c'; } + +.oi[data-glyph=envelope-open]:before { content:'\e05d'; } + +.oi[data-glyph=euro]:before { content:'\e05e'; } + +.oi[data-glyph=excerpt]:before { content:'\e05f'; } + +.oi[data-glyph=expand-down]:before { content:'\e060'; } + +.oi[data-glyph=expand-left]:before { content:'\e061'; } + +.oi[data-glyph=expand-right]:before { content:'\e062'; } + +.oi[data-glyph=expand-up]:before { content:'\e063'; } + +.oi[data-glyph=external-link]:before { content:'\e064'; } + +.oi[data-glyph=eye]:before { content:'\e065'; } + +.oi[data-glyph=eyedropper]:before { content:'\e066'; } + +.oi[data-glyph=file]:before { content:'\e067'; } + +.oi[data-glyph=fire]:before { content:'\e068'; } + +.oi[data-glyph=flag]:before { content:'\e069'; } + +.oi[data-glyph=flash]:before { content:'\e06a'; } + +.oi[data-glyph=folder]:before { content:'\e06b'; } + +.oi[data-glyph=fork]:before { content:'\e06c'; } + +.oi[data-glyph=fullscreen-enter]:before { content:'\e06d'; } + +.oi[data-glyph=fullscreen-exit]:before { content:'\e06e'; } + +.oi[data-glyph=globe]:before { content:'\e06f'; } + +.oi[data-glyph=graph]:before { content:'\e070'; } + +.oi[data-glyph=grid-four-up]:before { content:'\e071'; } + +.oi[data-glyph=grid-three-up]:before { content:'\e072'; } + +.oi[data-glyph=grid-two-up]:before { content:'\e073'; } + +.oi[data-glyph=hard-drive]:before { content:'\e074'; } + +.oi[data-glyph=header]:before { content:'\e075'; } + +.oi[data-glyph=headphones]:before { content:'\e076'; } + +.oi[data-glyph=heart]:before { content:'\e077'; } + +.oi[data-glyph=home]:before { content:'\e078'; } + +.oi[data-glyph=image]:before { content:'\e079'; } + +.oi[data-glyph=inbox]:before { content:'\e07a'; } + +.oi[data-glyph=infinity]:before { content:'\e07b'; } + +.oi[data-glyph=info]:before { content:'\e07c'; } + +.oi[data-glyph=italic]:before { content:'\e07d'; } + +.oi[data-glyph=justify-center]:before { content:'\e07e'; } + +.oi[data-glyph=justify-left]:before { content:'\e07f'; } + +.oi[data-glyph=justify-right]:before { content:'\e080'; } + +.oi[data-glyph=key]:before { content:'\e081'; } + +.oi[data-glyph=laptop]:before { content:'\e082'; } + +.oi[data-glyph=layers]:before { content:'\e083'; } + +.oi[data-glyph=lightbulb]:before { content:'\e084'; } + +.oi[data-glyph=link-broken]:before { content:'\e085'; } + +.oi[data-glyph=link-intact]:before { content:'\e086'; } + +.oi[data-glyph=list-rich]:before { content:'\e087'; } + +.oi[data-glyph=list]:before { content:'\e088'; } + +.oi[data-glyph=location]:before { content:'\e089'; } + +.oi[data-glyph=lock-locked]:before { content:'\e08a'; } + +.oi[data-glyph=lock-unlocked]:before { content:'\e08b'; } + +.oi[data-glyph=loop-circular]:before { content:'\e08c'; } + +.oi[data-glyph=loop-square]:before { content:'\e08d'; } + +.oi[data-glyph=loop]:before { content:'\e08e'; } + +.oi[data-glyph=magnifying-glass]:before { content:'\e08f'; } + +.oi[data-glyph=map-marker]:before { content:'\e090'; } + +.oi[data-glyph=map]:before { content:'\e091'; } + +.oi[data-glyph=media-pause]:before { content:'\e092'; } + +.oi[data-glyph=media-play]:before { content:'\e093'; } + +.oi[data-glyph=media-record]:before { content:'\e094'; } + +.oi[data-glyph=media-skip-backward]:before { content:'\e095'; } + +.oi[data-glyph=media-skip-forward]:before { content:'\e096'; } + +.oi[data-glyph=media-step-backward]:before { content:'\e097'; } + +.oi[data-glyph=media-step-forward]:before { content:'\e098'; } + +.oi[data-glyph=media-stop]:before { content:'\e099'; } + +.oi[data-glyph=medical-cross]:before { content:'\e09a'; } + +.oi[data-glyph=menu]:before { content:'\e09b'; } + +.oi[data-glyph=microphone]:before { content:'\e09c'; } + +.oi[data-glyph=minus]:before { content:'\e09d'; } + +.oi[data-glyph=monitor]:before { content:'\e09e'; } + +.oi[data-glyph=moon]:before { content:'\e09f'; } + +.oi[data-glyph=move]:before { content:'\e0a0'; } + +.oi[data-glyph=musical-note]:before { content:'\e0a1'; } + +.oi[data-glyph=paperclip]:before { content:'\e0a2'; } + +.oi[data-glyph=pencil]:before { content:'\e0a3'; } + +.oi[data-glyph=people]:before { content:'\e0a4'; } + +.oi[data-glyph=person]:before { content:'\e0a5'; } + +.oi[data-glyph=phone]:before { content:'\e0a6'; } + +.oi[data-glyph=pie-chart]:before { content:'\e0a7'; } + +.oi[data-glyph=pin]:before { content:'\e0a8'; } + +.oi[data-glyph=play-circle]:before { content:'\e0a9'; } + +.oi[data-glyph=plus]:before { content:'\e0aa'; } + +.oi[data-glyph=power-standby]:before { content:'\e0ab'; } + +.oi[data-glyph=print]:before { content:'\e0ac'; } + +.oi[data-glyph=project]:before { content:'\e0ad'; } + +.oi[data-glyph=pulse]:before { content:'\e0ae'; } + +.oi[data-glyph=puzzle-piece]:before { content:'\e0af'; } + +.oi[data-glyph=question-mark]:before { content:'\e0b0'; } + +.oi[data-glyph=rain]:before { content:'\e0b1'; } + +.oi[data-glyph=random]:before { content:'\e0b2'; } + +.oi[data-glyph=reload]:before { content:'\e0b3'; } + +.oi[data-glyph=resize-both]:before { content:'\e0b4'; } + +.oi[data-glyph=resize-height]:before { content:'\e0b5'; } + +.oi[data-glyph=resize-width]:before { content:'\e0b6'; } + +.oi[data-glyph=rss-alt]:before { content:'\e0b7'; } + +.oi[data-glyph=rss]:before { content:'\e0b8'; } + +.oi[data-glyph=script]:before { content:'\e0b9'; } + +.oi[data-glyph=share-boxed]:before { content:'\e0ba'; } + +.oi[data-glyph=share]:before { content:'\e0bb'; } + +.oi[data-glyph=shield]:before { content:'\e0bc'; } + +.oi[data-glyph=signal]:before { content:'\e0bd'; } + +.oi[data-glyph=signpost]:before { content:'\e0be'; } + +.oi[data-glyph=sort-ascending]:before { content:'\e0bf'; } + +.oi[data-glyph=sort-descending]:before { content:'\e0c0'; } + +.oi[data-glyph=spreadsheet]:before { content:'\e0c1'; } + +.oi[data-glyph=star]:before { content:'\e0c2'; } + +.oi[data-glyph=sun]:before { content:'\e0c3'; } + +.oi[data-glyph=tablet]:before { content:'\e0c4'; } + +.oi[data-glyph=tag]:before { content:'\e0c5'; } + +.oi[data-glyph=tags]:before { content:'\e0c6'; } + +.oi[data-glyph=target]:before { content:'\e0c7'; } + +.oi[data-glyph=task]:before { content:'\e0c8'; } + +.oi[data-glyph=terminal]:before { content:'\e0c9'; } + +.oi[data-glyph=text]:before { content:'\e0ca'; } + +.oi[data-glyph=thumb-down]:before { content:'\e0cb'; } + +.oi[data-glyph=thumb-up]:before { content:'\e0cc'; } + +.oi[data-glyph=timer]:before { content:'\e0cd'; } + +.oi[data-glyph=transfer]:before { content:'\e0ce'; } + +.oi[data-glyph=trash]:before { content:'\e0cf'; } + +.oi[data-glyph=underline]:before { content:'\e0d0'; } + +.oi[data-glyph=vertical-align-bottom]:before { content:'\e0d1'; } + +.oi[data-glyph=vertical-align-center]:before { content:'\e0d2'; } + +.oi[data-glyph=vertical-align-top]:before { content:'\e0d3'; } + +.oi[data-glyph=video]:before { content:'\e0d4'; } + +.oi[data-glyph=volume-high]:before { content:'\e0d5'; } + +.oi[data-glyph=volume-low]:before { content:'\e0d6'; } + +.oi[data-glyph=volume-off]:before { content:'\e0d7'; } + +.oi[data-glyph=warning]:before { content:'\e0d8'; } + +.oi[data-glyph=wifi]:before { content:'\e0d9'; } + +.oi[data-glyph=wrench]:before { content:'\e0da'; } + +.oi[data-glyph=x]:before { content:'\e0db'; } + +.oi[data-glyph=yen]:before { content:'\e0dc'; } + +.oi[data-glyph=zoom-in]:before { content:'\e0dd'; } + +.oi[data-glyph=zoom-out]:before { content:'\e0de'; } diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.less b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.less new file mode 100644 index 00000000..d505e9f2 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.less @@ -0,0 +1,962 @@ +@iconic-font-path: '../fonts/'; + +@font-face { + font-family: 'Icons'; + src: url('@{iconic-font-path}open-iconic.eot'); + src: url('@{iconic-font-path}open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('@{iconic-font-path}open-iconic.woff') format('woff'), url('@{iconic-font-path}open-iconic.ttf') format('truetype'), url('@{iconic-font-path}open-iconic.otf') format('opentype'), url('@{iconic-font-path}open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + +.oi[data-glyph].oi-text-replace { + font-size: 0; + line-height: 0; +} + +.oi[data-glyph].oi-text-replace:before { + width: 1em; + text-align: center; +} + +.oi[data-glyph] { + &:before { + position: relative; + top: 1px; + font-family: 'Icons'; + display: inline-block; + speak: none; + line-height: 1; + vertical-align: baseline; + font-weight: normal; + font-style: normal; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + } + + &:empty:before { + width: 1em; + text-align: center; + box-sizing: content-box; + } + + &.oi-align-left:before { + text-align: left; + } + &.oi-align-right:before { + text-align: right; + } + &.oi-align-center:before { + text-align: center; + } + + &.oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); + } + + &.oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); + } + + &.oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); + } +} + + +.oi[data-glyph=account-login]:before { + content: '\e000'; +} + +.oi[data-glyph=account-logout]:before { + content: '\e001'; +} + +.oi[data-glyph=action-redo]:before { + content: '\e002'; +} + +.oi[data-glyph=action-undo]:before { + content: '\e003'; +} + +.oi[data-glyph=align-center]:before { + content: '\e004'; +} + +.oi[data-glyph=align-left]:before { + content: '\e005'; +} + +.oi[data-glyph=align-right]:before { + content: '\e006'; +} + +.oi[data-glyph=aperture]:before { + content: '\e007'; +} + +.oi[data-glyph=arrow-bottom]:before { + content: '\e008'; +} + +.oi[data-glyph=arrow-circle-bottom]:before { + content: '\e009'; +} + +.oi[data-glyph=arrow-circle-left]:before { + content: '\e00a'; +} + +.oi[data-glyph=arrow-circle-right]:before { + content: '\e00b'; +} + +.oi[data-glyph=arrow-circle-top]:before { + content: '\e00c'; +} + +.oi[data-glyph=arrow-left]:before { + content: '\e00d'; +} + +.oi[data-glyph=arrow-right]:before { + content: '\e00e'; +} + +.oi[data-glyph=arrow-thick-bottom]:before { + content: '\e00f'; +} + +.oi[data-glyph=arrow-thick-left]:before { + content: '\e010'; +} + +.oi[data-glyph=arrow-thick-right]:before { + content: '\e011'; +} + +.oi[data-glyph=arrow-thick-top]:before { + content: '\e012'; +} + +.oi[data-glyph=arrow-top]:before { + content: '\e013'; +} + +.oi[data-glyph=audio-spectrum]:before { + content: '\e014'; +} + +.oi[data-glyph=audio]:before { + content: '\e015'; +} + +.oi[data-glyph=badge]:before { + content: '\e016'; +} + +.oi[data-glyph=ban]:before { + content: '\e017'; +} + +.oi[data-glyph=bar-chart]:before { + content: '\e018'; +} + +.oi[data-glyph=basket]:before { + content: '\e019'; +} + +.oi[data-glyph=battery-empty]:before { + content: '\e01a'; +} + +.oi[data-glyph=battery-full]:before { + content: '\e01b'; +} + +.oi[data-glyph=beaker]:before { + content: '\e01c'; +} + +.oi[data-glyph=bell]:before { + content: '\e01d'; +} + +.oi[data-glyph=bluetooth]:before { + content: '\e01e'; +} + +.oi[data-glyph=bold]:before { + content: '\e01f'; +} + +.oi[data-glyph=bolt]:before { + content: '\e020'; +} + +.oi[data-glyph=book]:before { + content: '\e021'; +} + +.oi[data-glyph=bookmark]:before { + content: '\e022'; +} + +.oi[data-glyph=box]:before { + content: '\e023'; +} + +.oi[data-glyph=briefcase]:before { + content: '\e024'; +} + +.oi[data-glyph=british-pound]:before { + content: '\e025'; +} + +.oi[data-glyph=browser]:before { + content: '\e026'; +} + +.oi[data-glyph=brush]:before { + content: '\e027'; +} + +.oi[data-glyph=bug]:before { + content: '\e028'; +} + +.oi[data-glyph=bullhorn]:before { + content: '\e029'; +} + +.oi[data-glyph=calculator]:before { + content: '\e02a'; +} + +.oi[data-glyph=calendar]:before { + content: '\e02b'; +} + +.oi[data-glyph=camera-slr]:before { + content: '\e02c'; +} + +.oi[data-glyph=caret-bottom]:before { + content: '\e02d'; +} + +.oi[data-glyph=caret-left]:before { + content: '\e02e'; +} + +.oi[data-glyph=caret-right]:before { + content: '\e02f'; +} + +.oi[data-glyph=caret-top]:before { + content: '\e030'; +} + +.oi[data-glyph=cart]:before { + content: '\e031'; +} + +.oi[data-glyph=chat]:before { + content: '\e032'; +} + +.oi[data-glyph=check]:before { + content: '\e033'; +} + +.oi[data-glyph=chevron-bottom]:before { + content: '\e034'; +} + +.oi[data-glyph=chevron-left]:before { + content: '\e035'; +} + +.oi[data-glyph=chevron-right]:before { + content: '\e036'; +} + +.oi[data-glyph=chevron-top]:before { + content: '\e037'; +} + +.oi[data-glyph=circle-check]:before { + content: '\e038'; +} + +.oi[data-glyph=circle-x]:before { + content: '\e039'; +} + +.oi[data-glyph=clipboard]:before { + content: '\e03a'; +} + +.oi[data-glyph=clock]:before { + content: '\e03b'; +} + +.oi[data-glyph=cloud-download]:before { + content: '\e03c'; +} + +.oi[data-glyph=cloud-upload]:before { + content: '\e03d'; +} + +.oi[data-glyph=cloud]:before { + content: '\e03e'; +} + +.oi[data-glyph=cloudy]:before { + content: '\e03f'; +} + +.oi[data-glyph=code]:before { + content: '\e040'; +} + +.oi[data-glyph=cog]:before { + content: '\e041'; +} + +.oi[data-glyph=collapse-down]:before { + content: '\e042'; +} + +.oi[data-glyph=collapse-left]:before { + content: '\e043'; +} + +.oi[data-glyph=collapse-right]:before { + content: '\e044'; +} + +.oi[data-glyph=collapse-up]:before { + content: '\e045'; +} + +.oi[data-glyph=command]:before { + content: '\e046'; +} + +.oi[data-glyph=comment-square]:before { + content: '\e047'; +} + +.oi[data-glyph=compass]:before { + content: '\e048'; +} + +.oi[data-glyph=contrast]:before { + content: '\e049'; +} + +.oi[data-glyph=copywriting]:before { + content: '\e04a'; +} + +.oi[data-glyph=credit-card]:before { + content: '\e04b'; +} + +.oi[data-glyph=crop]:before { + content: '\e04c'; +} + +.oi[data-glyph=dashboard]:before { + content: '\e04d'; +} + +.oi[data-glyph=data-transfer-download]:before { + content: '\e04e'; +} + +.oi[data-glyph=data-transfer-upload]:before { + content: '\e04f'; +} + +.oi[data-glyph=delete]:before { + content: '\e050'; +} + +.oi[data-glyph=dial]:before { + content: '\e051'; +} + +.oi[data-glyph=document]:before { + content: '\e052'; +} + +.oi[data-glyph=dollar]:before { + content: '\e053'; +} + +.oi[data-glyph=double-quote-sans-left]:before { + content: '\e054'; +} + +.oi[data-glyph=double-quote-sans-right]:before { + content: '\e055'; +} + +.oi[data-glyph=double-quote-serif-left]:before { + content: '\e056'; +} + +.oi[data-glyph=double-quote-serif-right]:before { + content: '\e057'; +} + +.oi[data-glyph=droplet]:before { + content: '\e058'; +} + +.oi[data-glyph=eject]:before { + content: '\e059'; +} + +.oi[data-glyph=elevator]:before { + content: '\e05a'; +} + +.oi[data-glyph=ellipses]:before { + content: '\e05b'; +} + +.oi[data-glyph=envelope-closed]:before { + content: '\e05c'; +} + +.oi[data-glyph=envelope-open]:before { + content: '\e05d'; +} + +.oi[data-glyph=euro]:before { + content: '\e05e'; +} + +.oi[data-glyph=excerpt]:before { + content: '\e05f'; +} + +.oi[data-glyph=expand-down]:before { + content: '\e060'; +} + +.oi[data-glyph=expand-left]:before { + content: '\e061'; +} + +.oi[data-glyph=expand-right]:before { + content: '\e062'; +} + +.oi[data-glyph=expand-up]:before { + content: '\e063'; +} + +.oi[data-glyph=external-link]:before { + content: '\e064'; +} + +.oi[data-glyph=eye]:before { + content: '\e065'; +} + +.oi[data-glyph=eyedropper]:before { + content: '\e066'; +} + +.oi[data-glyph=file]:before { + content: '\e067'; +} + +.oi[data-glyph=fire]:before { + content: '\e068'; +} + +.oi[data-glyph=flag]:before { + content: '\e069'; +} + +.oi[data-glyph=flash]:before { + content: '\e06a'; +} + +.oi[data-glyph=folder]:before { + content: '\e06b'; +} + +.oi[data-glyph=fork]:before { + content: '\e06c'; +} + +.oi[data-glyph=fullscreen-enter]:before { + content: '\e06d'; +} + +.oi[data-glyph=fullscreen-exit]:before { + content: '\e06e'; +} + +.oi[data-glyph=globe]:before { + content: '\e06f'; +} + +.oi[data-glyph=graph]:before { + content: '\e070'; +} + +.oi[data-glyph=grid-four-up]:before { + content: '\e071'; +} + +.oi[data-glyph=grid-three-up]:before { + content: '\e072'; +} + +.oi[data-glyph=grid-two-up]:before { + content: '\e073'; +} + +.oi[data-glyph=hard-drive]:before { + content: '\e074'; +} + +.oi[data-glyph=header]:before { + content: '\e075'; +} + +.oi[data-glyph=headphones]:before { + content: '\e076'; +} + +.oi[data-glyph=heart]:before { + content: '\e077'; +} + +.oi[data-glyph=home]:before { + content: '\e078'; +} + +.oi[data-glyph=image]:before { + content: '\e079'; +} + +.oi[data-glyph=inbox]:before { + content: '\e07a'; +} + +.oi[data-glyph=infinity]:before { + content: '\e07b'; +} + +.oi[data-glyph=info]:before { + content: '\e07c'; +} + +.oi[data-glyph=italic]:before { + content: '\e07d'; +} + +.oi[data-glyph=justify-center]:before { + content: '\e07e'; +} + +.oi[data-glyph=justify-left]:before { + content: '\e07f'; +} + +.oi[data-glyph=justify-right]:before { + content: '\e080'; +} + +.oi[data-glyph=key]:before { + content: '\e081'; +} + +.oi[data-glyph=laptop]:before { + content: '\e082'; +} + +.oi[data-glyph=layers]:before { + content: '\e083'; +} + +.oi[data-glyph=lightbulb]:before { + content: '\e084'; +} + +.oi[data-glyph=link-broken]:before { + content: '\e085'; +} + +.oi[data-glyph=link-intact]:before { + content: '\e086'; +} + +.oi[data-glyph=list-rich]:before { + content: '\e087'; +} + +.oi[data-glyph=list]:before { + content: '\e088'; +} + +.oi[data-glyph=location]:before { + content: '\e089'; +} + +.oi[data-glyph=lock-locked]:before { + content: '\e08a'; +} + +.oi[data-glyph=lock-unlocked]:before { + content: '\e08b'; +} + +.oi[data-glyph=loop-circular]:before { + content: '\e08c'; +} + +.oi[data-glyph=loop-square]:before { + content: '\e08d'; +} + +.oi[data-glyph=loop]:before { + content: '\e08e'; +} + +.oi[data-glyph=magnifying-glass]:before { + content: '\e08f'; +} + +.oi[data-glyph=map-marker]:before { + content: '\e090'; +} + +.oi[data-glyph=map]:before { + content: '\e091'; +} + +.oi[data-glyph=media-pause]:before { + content: '\e092'; +} + +.oi[data-glyph=media-play]:before { + content: '\e093'; +} + +.oi[data-glyph=media-record]:before { + content: '\e094'; +} + +.oi[data-glyph=media-skip-backward]:before { + content: '\e095'; +} + +.oi[data-glyph=media-skip-forward]:before { + content: '\e096'; +} + +.oi[data-glyph=media-step-backward]:before { + content: '\e097'; +} + +.oi[data-glyph=media-step-forward]:before { + content: '\e098'; +} + +.oi[data-glyph=media-stop]:before { + content: '\e099'; +} + +.oi[data-glyph=medical-cross]:before { + content: '\e09a'; +} + +.oi[data-glyph=menu]:before { + content: '\e09b'; +} + +.oi[data-glyph=microphone]:before { + content: '\e09c'; +} + +.oi[data-glyph=minus]:before { + content: '\e09d'; +} + +.oi[data-glyph=monitor]:before { + content: '\e09e'; +} + +.oi[data-glyph=moon]:before { + content: '\e09f'; +} + +.oi[data-glyph=move]:before { + content: '\e0a0'; +} + +.oi[data-glyph=musical-note]:before { + content: '\e0a1'; +} + +.oi[data-glyph=paperclip]:before { + content: '\e0a2'; +} + +.oi[data-glyph=pencil]:before { + content: '\e0a3'; +} + +.oi[data-glyph=people]:before { + content: '\e0a4'; +} + +.oi[data-glyph=person]:before { + content: '\e0a5'; +} + +.oi[data-glyph=phone]:before { + content: '\e0a6'; +} + +.oi[data-glyph=pie-chart]:before { + content: '\e0a7'; +} + +.oi[data-glyph=pin]:before { + content: '\e0a8'; +} + +.oi[data-glyph=play-circle]:before { + content: '\e0a9'; +} + +.oi[data-glyph=plus]:before { + content: '\e0aa'; +} + +.oi[data-glyph=power-standby]:before { + content: '\e0ab'; +} + +.oi[data-glyph=print]:before { + content: '\e0ac'; +} + +.oi[data-glyph=project]:before { + content: '\e0ad'; +} + +.oi[data-glyph=pulse]:before { + content: '\e0ae'; +} + +.oi[data-glyph=puzzle-piece]:before { + content: '\e0af'; +} + +.oi[data-glyph=question-mark]:before { + content: '\e0b0'; +} + +.oi[data-glyph=rain]:before { + content: '\e0b1'; +} + +.oi[data-glyph=random]:before { + content: '\e0b2'; +} + +.oi[data-glyph=reload]:before { + content: '\e0b3'; +} + +.oi[data-glyph=resize-both]:before { + content: '\e0b4'; +} + +.oi[data-glyph=resize-height]:before { + content: '\e0b5'; +} + +.oi[data-glyph=resize-width]:before { + content: '\e0b6'; +} + +.oi[data-glyph=rss-alt]:before { + content: '\e0b7'; +} + +.oi[data-glyph=rss]:before { + content: '\e0b8'; +} + +.oi[data-glyph=script]:before { + content: '\e0b9'; +} + +.oi[data-glyph=share-boxed]:before { + content: '\e0ba'; +} + +.oi[data-glyph=share]:before { + content: '\e0bb'; +} + +.oi[data-glyph=shield]:before { + content: '\e0bc'; +} + +.oi[data-glyph=signal]:before { + content: '\e0bd'; +} + +.oi[data-glyph=signpost]:before { + content: '\e0be'; +} + +.oi[data-glyph=sort-ascending]:before { + content: '\e0bf'; +} + +.oi[data-glyph=sort-descending]:before { + content: '\e0c0'; +} + +.oi[data-glyph=spreadsheet]:before { + content: '\e0c1'; +} + +.oi[data-glyph=star]:before { + content: '\e0c2'; +} + +.oi[data-glyph=sun]:before { + content: '\e0c3'; +} + +.oi[data-glyph=tablet]:before { + content: '\e0c4'; +} + +.oi[data-glyph=tag]:before { + content: '\e0c5'; +} + +.oi[data-glyph=tags]:before { + content: '\e0c6'; +} + +.oi[data-glyph=target]:before { + content: '\e0c7'; +} + +.oi[data-glyph=task]:before { + content: '\e0c8'; +} + +.oi[data-glyph=terminal]:before { + content: '\e0c9'; +} + +.oi[data-glyph=text]:before { + content: '\e0ca'; +} + +.oi[data-glyph=thumb-down]:before { + content: '\e0cb'; +} + +.oi[data-glyph=thumb-up]:before { + content: '\e0cc'; +} + +.oi[data-glyph=timer]:before { + content: '\e0cd'; +} + +.oi[data-glyph=transfer]:before { + content: '\e0ce'; +} + +.oi[data-glyph=trash]:before { + content: '\e0cf'; +} + +.oi[data-glyph=underline]:before { + content: '\e0d0'; +} + +.oi[data-glyph=vertical-align-bottom]:before { + content: '\e0d1'; +} + +.oi[data-glyph=vertical-align-center]:before { + content: '\e0d2'; +} + +.oi[data-glyph=vertical-align-top]:before { + content: '\e0d3'; +} + +.oi[data-glyph=video]:before { + content: '\e0d4'; +} + +.oi[data-glyph=volume-high]:before { + content: '\e0d5'; +} + +.oi[data-glyph=volume-low]:before { + content: '\e0d6'; +} + +.oi[data-glyph=volume-off]:before { + content: '\e0d7'; +} + +.oi[data-glyph=warning]:before { + content: '\e0d8'; +} + +.oi[data-glyph=wifi]:before { + content: '\e0d9'; +} + +.oi[data-glyph=wrench]:before { + content: '\e0da'; +} + +.oi[data-glyph=x]:before { + content: '\e0db'; +} + +.oi[data-glyph=yen]:before { + content: '\e0dc'; +} + +.oi[data-glyph=zoom-in]:before { + content: '\e0dd'; +} + +.oi[data-glyph=zoom-out]:before { + content: '\e0de'; +} diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.min.css b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.min.css new file mode 100644 index 00000000..1f6afb82 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.min.css @@ -0,0 +1 @@ +@font-face{font-family:Icons;src:url(../fonts/open-iconic.eot);src:url(../fonts/open-iconic.eot?#iconic-sm) format('embedded-opentype'),url(../fonts/open-iconic.woff) format('woff'),url(../fonts/open-iconic.ttf) format('truetype'),url(../fonts/open-iconic.otf) format('opentype'),url(../fonts/open-iconic.svg#iconic-sm) format('svg');font-weight:400;font-style:normal}.oi[data-glyph].oi-text-replace{font-size:0;line-height:0}.oi[data-glyph].oi-text-replace:before{width:1em;text-align:center}.oi[data-glyph]:before{font-family:Icons;display:inline-block;speak:none;line-height:1;vertical-align:baseline;font-weight:400;font-style:normal;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.oi[data-glyph]:empty:before{width:1em;text-align:center;box-sizing:content-box}.oi[data-glyph].oi-align-left:before{text-align:left}.oi[data-glyph].oi-align-right:before{text-align:right}.oi[data-glyph].oi-align-center:before{text-align:center}.oi[data-glyph].oi-flip-horizontal:before{-webkit-transform:scale(-1,1);-ms-transform:scale(-1,1);transform:scale(-1,1)}.oi[data-glyph].oi-flip-vertical:before{-webkit-transform:scale(1,-1);-ms-transform:scale(-1,1);transform:scale(1,-1)}.oi[data-glyph].oi-flip-horizontal-vertical:before{-webkit-transform:scale(-1,-1);-ms-transform:scale(-1,1);transform:scale(-1,-1)}.oi[data-glyph=account-login]:before{content:'\e000'}.oi[data-glyph=account-logout]:before{content:'\e001'}.oi[data-glyph=action-redo]:before{content:'\e002'}.oi[data-glyph=action-undo]:before{content:'\e003'}.oi[data-glyph=align-center]:before{content:'\e004'}.oi[data-glyph=align-left]:before{content:'\e005'}.oi[data-glyph=align-right]:before{content:'\e006'}.oi[data-glyph=aperture]:before{content:'\e007'}.oi[data-glyph=arrow-bottom]:before{content:'\e008'}.oi[data-glyph=arrow-circle-bottom]:before{content:'\e009'}.oi[data-glyph=arrow-circle-left]:before{content:'\e00a'}.oi[data-glyph=arrow-circle-right]:before{content:'\e00b'}.oi[data-glyph=arrow-circle-top]:before{content:'\e00c'}.oi[data-glyph=arrow-left]:before{content:'\e00d'}.oi[data-glyph=arrow-right]:before{content:'\e00e'}.oi[data-glyph=arrow-thick-bottom]:before{content:'\e00f'}.oi[data-glyph=arrow-thick-left]:before{content:'\e010'}.oi[data-glyph=arrow-thick-right]:before{content:'\e011'}.oi[data-glyph=arrow-thick-top]:before{content:'\e012'}.oi[data-glyph=arrow-top]:before{content:'\e013'}.oi[data-glyph=audio-spectrum]:before{content:'\e014'}.oi[data-glyph=audio]:before{content:'\e015'}.oi[data-glyph=badge]:before{content:'\e016'}.oi[data-glyph=ban]:before{content:'\e017'}.oi[data-glyph=bar-chart]:before{content:'\e018'}.oi[data-glyph=basket]:before{content:'\e019'}.oi[data-glyph=battery-empty]:before{content:'\e01a'}.oi[data-glyph=battery-full]:before{content:'\e01b'}.oi[data-glyph=beaker]:before{content:'\e01c'}.oi[data-glyph=bell]:before{content:'\e01d'}.oi[data-glyph=bluetooth]:before{content:'\e01e'}.oi[data-glyph=bold]:before{content:'\e01f'}.oi[data-glyph=bolt]:before{content:'\e020'}.oi[data-glyph=book]:before{content:'\e021'}.oi[data-glyph=bookmark]:before{content:'\e022'}.oi[data-glyph=box]:before{content:'\e023'}.oi[data-glyph=briefcase]:before{content:'\e024'}.oi[data-glyph=british-pound]:before{content:'\e025'}.oi[data-glyph=browser]:before{content:'\e026'}.oi[data-glyph=brush]:before{content:'\e027'}.oi[data-glyph=bug]:before{content:'\e028'}.oi[data-glyph=bullhorn]:before{content:'\e029'}.oi[data-glyph=calculator]:before{content:'\e02a'}.oi[data-glyph=calendar]:before{content:'\e02b'}.oi[data-glyph=camera-slr]:before{content:'\e02c'}.oi[data-glyph=caret-bottom]:before{content:'\e02d'}.oi[data-glyph=caret-left]:before{content:'\e02e'}.oi[data-glyph=caret-right]:before{content:'\e02f'}.oi[data-glyph=caret-top]:before{content:'\e030'}.oi[data-glyph=cart]:before{content:'\e031'}.oi[data-glyph=chat]:before{content:'\e032'}.oi[data-glyph=check]:before{content:'\e033'}.oi[data-glyph=chevron-bottom]:before{content:'\e034'}.oi[data-glyph=chevron-left]:before{content:'\e035'}.oi[data-glyph=chevron-right]:before{content:'\e036'}.oi[data-glyph=chevron-top]:before{content:'\e037'}.oi[data-glyph=circle-check]:before{content:'\e038'}.oi[data-glyph=circle-x]:before{content:'\e039'}.oi[data-glyph=clipboard]:before{content:'\e03a'}.oi[data-glyph=clock]:before{content:'\e03b'}.oi[data-glyph=cloud-download]:before{content:'\e03c'}.oi[data-glyph=cloud-upload]:before{content:'\e03d'}.oi[data-glyph=cloud]:before{content:'\e03e'}.oi[data-glyph=cloudy]:before{content:'\e03f'}.oi[data-glyph=code]:before{content:'\e040'}.oi[data-glyph=cog]:before{content:'\e041'}.oi[data-glyph=collapse-down]:before{content:'\e042'}.oi[data-glyph=collapse-left]:before{content:'\e043'}.oi[data-glyph=collapse-right]:before{content:'\e044'}.oi[data-glyph=collapse-up]:before{content:'\e045'}.oi[data-glyph=command]:before{content:'\e046'}.oi[data-glyph=comment-square]:before{content:'\e047'}.oi[data-glyph=compass]:before{content:'\e048'}.oi[data-glyph=contrast]:before{content:'\e049'}.oi[data-glyph=copywriting]:before{content:'\e04a'}.oi[data-glyph=credit-card]:before{content:'\e04b'}.oi[data-glyph=crop]:before{content:'\e04c'}.oi[data-glyph=dashboard]:before{content:'\e04d'}.oi[data-glyph=data-transfer-download]:before{content:'\e04e'}.oi[data-glyph=data-transfer-upload]:before{content:'\e04f'}.oi[data-glyph=delete]:before{content:'\e050'}.oi[data-glyph=dial]:before{content:'\e051'}.oi[data-glyph=document]:before{content:'\e052'}.oi[data-glyph=dollar]:before{content:'\e053'}.oi[data-glyph=double-quote-sans-left]:before{content:'\e054'}.oi[data-glyph=double-quote-sans-right]:before{content:'\e055'}.oi[data-glyph=double-quote-serif-left]:before{content:'\e056'}.oi[data-glyph=double-quote-serif-right]:before{content:'\e057'}.oi[data-glyph=droplet]:before{content:'\e058'}.oi[data-glyph=eject]:before{content:'\e059'}.oi[data-glyph=elevator]:before{content:'\e05a'}.oi[data-glyph=ellipses]:before{content:'\e05b'}.oi[data-glyph=envelope-closed]:before{content:'\e05c'}.oi[data-glyph=envelope-open]:before{content:'\e05d'}.oi[data-glyph=euro]:before{content:'\e05e'}.oi[data-glyph=excerpt]:before{content:'\e05f'}.oi[data-glyph=expand-down]:before{content:'\e060'}.oi[data-glyph=expand-left]:before{content:'\e061'}.oi[data-glyph=expand-right]:before{content:'\e062'}.oi[data-glyph=expand-up]:before{content:'\e063'}.oi[data-glyph=external-link]:before{content:'\e064'}.oi[data-glyph=eye]:before{content:'\e065'}.oi[data-glyph=eyedropper]:before{content:'\e066'}.oi[data-glyph=file]:before{content:'\e067'}.oi[data-glyph=fire]:before{content:'\e068'}.oi[data-glyph=flag]:before{content:'\e069'}.oi[data-glyph=flash]:before{content:'\e06a'}.oi[data-glyph=folder]:before{content:'\e06b'}.oi[data-glyph=fork]:before{content:'\e06c'}.oi[data-glyph=fullscreen-enter]:before{content:'\e06d'}.oi[data-glyph=fullscreen-exit]:before{content:'\e06e'}.oi[data-glyph=globe]:before{content:'\e06f'}.oi[data-glyph=graph]:before{content:'\e070'}.oi[data-glyph=grid-four-up]:before{content:'\e071'}.oi[data-glyph=grid-three-up]:before{content:'\e072'}.oi[data-glyph=grid-two-up]:before{content:'\e073'}.oi[data-glyph=hard-drive]:before{content:'\e074'}.oi[data-glyph=header]:before{content:'\e075'}.oi[data-glyph=headphones]:before{content:'\e076'}.oi[data-glyph=heart]:before{content:'\e077'}.oi[data-glyph=home]:before{content:'\e078'}.oi[data-glyph=image]:before{content:'\e079'}.oi[data-glyph=inbox]:before{content:'\e07a'}.oi[data-glyph=infinity]:before{content:'\e07b'}.oi[data-glyph=info]:before{content:'\e07c'}.oi[data-glyph=italic]:before{content:'\e07d'}.oi[data-glyph=justify-center]:before{content:'\e07e'}.oi[data-glyph=justify-left]:before{content:'\e07f'}.oi[data-glyph=justify-right]:before{content:'\e080'}.oi[data-glyph=key]:before{content:'\e081'}.oi[data-glyph=laptop]:before{content:'\e082'}.oi[data-glyph=layers]:before{content:'\e083'}.oi[data-glyph=lightbulb]:before{content:'\e084'}.oi[data-glyph=link-broken]:before{content:'\e085'}.oi[data-glyph=link-intact]:before{content:'\e086'}.oi[data-glyph=list-rich]:before{content:'\e087'}.oi[data-glyph=list]:before{content:'\e088'}.oi[data-glyph=location]:before{content:'\e089'}.oi[data-glyph=lock-locked]:before{content:'\e08a'}.oi[data-glyph=lock-unlocked]:before{content:'\e08b'}.oi[data-glyph=loop-circular]:before{content:'\e08c'}.oi[data-glyph=loop-square]:before{content:'\e08d'}.oi[data-glyph=loop]:before{content:'\e08e'}.oi[data-glyph=magnifying-glass]:before{content:'\e08f'}.oi[data-glyph=map-marker]:before{content:'\e090'}.oi[data-glyph=map]:before{content:'\e091'}.oi[data-glyph=media-pause]:before{content:'\e092'}.oi[data-glyph=media-play]:before{content:'\e093'}.oi[data-glyph=media-record]:before{content:'\e094'}.oi[data-glyph=media-skip-backward]:before{content:'\e095'}.oi[data-glyph=media-skip-forward]:before{content:'\e096'}.oi[data-glyph=media-step-backward]:before{content:'\e097'}.oi[data-glyph=media-step-forward]:before{content:'\e098'}.oi[data-glyph=media-stop]:before{content:'\e099'}.oi[data-glyph=medical-cross]:before{content:'\e09a'}.oi[data-glyph=menu]:before{content:'\e09b'}.oi[data-glyph=microphone]:before{content:'\e09c'}.oi[data-glyph=minus]:before{content:'\e09d'}.oi[data-glyph=monitor]:before{content:'\e09e'}.oi[data-glyph=moon]:before{content:'\e09f'}.oi[data-glyph=move]:before{content:'\e0a0'}.oi[data-glyph=musical-note]:before{content:'\e0a1'}.oi[data-glyph=paperclip]:before{content:'\e0a2'}.oi[data-glyph=pencil]:before{content:'\e0a3'}.oi[data-glyph=people]:before{content:'\e0a4'}.oi[data-glyph=person]:before{content:'\e0a5'}.oi[data-glyph=phone]:before{content:'\e0a6'}.oi[data-glyph=pie-chart]:before{content:'\e0a7'}.oi[data-glyph=pin]:before{content:'\e0a8'}.oi[data-glyph=play-circle]:before{content:'\e0a9'}.oi[data-glyph=plus]:before{content:'\e0aa'}.oi[data-glyph=power-standby]:before{content:'\e0ab'}.oi[data-glyph=print]:before{content:'\e0ac'}.oi[data-glyph=project]:before{content:'\e0ad'}.oi[data-glyph=pulse]:before{content:'\e0ae'}.oi[data-glyph=puzzle-piece]:before{content:'\e0af'}.oi[data-glyph=question-mark]:before{content:'\e0b0'}.oi[data-glyph=rain]:before{content:'\e0b1'}.oi[data-glyph=random]:before{content:'\e0b2'}.oi[data-glyph=reload]:before{content:'\e0b3'}.oi[data-glyph=resize-both]:before{content:'\e0b4'}.oi[data-glyph=resize-height]:before{content:'\e0b5'}.oi[data-glyph=resize-width]:before{content:'\e0b6'}.oi[data-glyph=rss-alt]:before{content:'\e0b7'}.oi[data-glyph=rss]:before{content:'\e0b8'}.oi[data-glyph=script]:before{content:'\e0b9'}.oi[data-glyph=share-boxed]:before{content:'\e0ba'}.oi[data-glyph=share]:before{content:'\e0bb'}.oi[data-glyph=shield]:before{content:'\e0bc'}.oi[data-glyph=signal]:before{content:'\e0bd'}.oi[data-glyph=signpost]:before{content:'\e0be'}.oi[data-glyph=sort-ascending]:before{content:'\e0bf'}.oi[data-glyph=sort-descending]:before{content:'\e0c0'}.oi[data-glyph=spreadsheet]:before{content:'\e0c1'}.oi[data-glyph=star]:before{content:'\e0c2'}.oi[data-glyph=sun]:before{content:'\e0c3'}.oi[data-glyph=tablet]:before{content:'\e0c4'}.oi[data-glyph=tag]:before{content:'\e0c5'}.oi[data-glyph=tags]:before{content:'\e0c6'}.oi[data-glyph=target]:before{content:'\e0c7'}.oi[data-glyph=task]:before{content:'\e0c8'}.oi[data-glyph=terminal]:before{content:'\e0c9'}.oi[data-glyph=text]:before{content:'\e0ca'}.oi[data-glyph=thumb-down]:before{content:'\e0cb'}.oi[data-glyph=thumb-up]:before{content:'\e0cc'}.oi[data-glyph=timer]:before{content:'\e0cd'}.oi[data-glyph=transfer]:before{content:'\e0ce'}.oi[data-glyph=trash]:before{content:'\e0cf'}.oi[data-glyph=underline]:before{content:'\e0d0'}.oi[data-glyph=vertical-align-bottom]:before{content:'\e0d1'}.oi[data-glyph=vertical-align-center]:before{content:'\e0d2'}.oi[data-glyph=vertical-align-top]:before{content:'\e0d3'}.oi[data-glyph=video]:before{content:'\e0d4'}.oi[data-glyph=volume-high]:before{content:'\e0d5'}.oi[data-glyph=volume-low]:before{content:'\e0d6'}.oi[data-glyph=volume-off]:before{content:'\e0d7'}.oi[data-glyph=warning]:before{content:'\e0d8'}.oi[data-glyph=wifi]:before{content:'\e0d9'}.oi[data-glyph=wrench]:before{content:'\e0da'}.oi[data-glyph=x]:before{content:'\e0db'}.oi[data-glyph=yen]:before{content:'\e0dc'}.oi[data-glyph=zoom-in]:before{content:'\e0dd'}.oi[data-glyph=zoom-out]:before{content:'\e0de'} \ No newline at end of file diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.scss b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.scss new file mode 100644 index 00000000..e03d979f --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.scss @@ -0,0 +1,963 @@ +$iconic-font-path: '../fonts/' !default; + +@font-face { + font-family: 'Icons'; + src: url('#{$iconic-font-path}open-iconic.eot'); + src: url('#{$iconic-font-path}open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('#{$iconic-font-path}open-iconic.woff') format('woff'), url('#{$iconic-font-path}open-iconic.ttf') format('truetype'), url('#{$iconic-font-path}open-iconic.otf') format('opentype'), url('#{$iconic-font-path}open-iconic.svg#iconic-sm') format('svg'); + font-weight: normal; + font-style: normal; +} + +.oi[data-glyph].oi-text-replace { + font-size: 0; + line-height: 0; +} + +.oi[data-glyph].oi-text-replace:before { + width: 1em; + text-align: center; +} + +.oi[data-glyph] { + &:before { + position: relative; + top: 1px; + font-family: 'Icons'; + display: inline-block; + speak: none; + line-height: 1; + vertical-align: baseline; + font-weight: normal; + font-style: normal; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; + } + + &:empty:before { + width: 1em; + text-align: center; + box-sizing: content-box; + } + + &.oi-align-left:before { + text-align: left; + } + &.oi-align-right:before { + text-align: right; + } + &.oi-align-center:before { + text-align: center; + } + + &.oi-flip-horizontal:before { + -webkit-transform: scale(-1, 1); + -ms-transform: scale(-1, 1); + transform: scale(-1, 1); + } + + &.oi-flip-vertical:before { + -webkit-transform: scale(1, -1); + -ms-transform: scale(-1, 1); + transform: scale(1, -1); + } + + &.oi-flip-horizontal-vertical:before { + -webkit-transform: scale(-1, -1); + -ms-transform: scale(-1, 1); + transform: scale(-1, -1); + } +} + + +.oi[data-glyph=account-login]:before { + content: '\e000'; +} + +.oi[data-glyph=account-logout]:before { + content: '\e001'; +} + +.oi[data-glyph=action-redo]:before { + content: '\e002'; +} + +.oi[data-glyph=action-undo]:before { + content: '\e003'; +} + +.oi[data-glyph=align-center]:before { + content: '\e004'; +} + +.oi[data-glyph=align-left]:before { + content: '\e005'; +} + +.oi[data-glyph=align-right]:before { + content: '\e006'; +} + +.oi[data-glyph=aperture]:before { + content: '\e007'; +} + +.oi[data-glyph=arrow-bottom]:before { + content: '\e008'; +} + +.oi[data-glyph=arrow-circle-bottom]:before { + content: '\e009'; +} + +.oi[data-glyph=arrow-circle-left]:before { + content: '\e00a'; +} + +.oi[data-glyph=arrow-circle-right]:before { + content: '\e00b'; +} + +.oi[data-glyph=arrow-circle-top]:before { + content: '\e00c'; +} + +.oi[data-glyph=arrow-left]:before { + content: '\e00d'; +} + +.oi[data-glyph=arrow-right]:before { + content: '\e00e'; +} + +.oi[data-glyph=arrow-thick-bottom]:before { + content: '\e00f'; +} + +.oi[data-glyph=arrow-thick-left]:before { + content: '\e010'; +} + +.oi[data-glyph=arrow-thick-right]:before { + content: '\e011'; +} + +.oi[data-glyph=arrow-thick-top]:before { + content: '\e012'; +} + +.oi[data-glyph=arrow-top]:before { + content: '\e013'; +} + +.oi[data-glyph=audio-spectrum]:before { + content: '\e014'; +} + +.oi[data-glyph=audio]:before { + content: '\e015'; +} + +.oi[data-glyph=badge]:before { + content: '\e016'; +} + +.oi[data-glyph=ban]:before { + content: '\e017'; +} + +.oi[data-glyph=bar-chart]:before { + content: '\e018'; +} + +.oi[data-glyph=basket]:before { + content: '\e019'; +} + +.oi[data-glyph=battery-empty]:before { + content: '\e01a'; +} + +.oi[data-glyph=battery-full]:before { + content: '\e01b'; +} + +.oi[data-glyph=beaker]:before { + content: '\e01c'; +} + +.oi[data-glyph=bell]:before { + content: '\e01d'; +} + +.oi[data-glyph=bluetooth]:before { + content: '\e01e'; +} + +.oi[data-glyph=bold]:before { + content: '\e01f'; +} + +.oi[data-glyph=bolt]:before { + content: '\e020'; +} + +.oi[data-glyph=book]:before { + content: '\e021'; +} + +.oi[data-glyph=bookmark]:before { + content: '\e022'; +} + +.oi[data-glyph=box]:before { + content: '\e023'; +} + +.oi[data-glyph=briefcase]:before { + content: '\e024'; +} + +.oi[data-glyph=british-pound]:before { + content: '\e025'; +} + +.oi[data-glyph=browser]:before { + content: '\e026'; +} + +.oi[data-glyph=brush]:before { + content: '\e027'; +} + +.oi[data-glyph=bug]:before { + content: '\e028'; +} + +.oi[data-glyph=bullhorn]:before { + content: '\e029'; +} + +.oi[data-glyph=calculator]:before { + content: '\e02a'; +} + +.oi[data-glyph=calendar]:before { + content: '\e02b'; +} + +.oi[data-glyph=camera-slr]:before { + content: '\e02c'; +} + +.oi[data-glyph=caret-bottom]:before { + content: '\e02d'; +} + +.oi[data-glyph=caret-left]:before { + content: '\e02e'; +} + +.oi[data-glyph=caret-right]:before { + content: '\e02f'; +} + +.oi[data-glyph=caret-top]:before { + content: '\e030'; +} + +.oi[data-glyph=cart]:before { + content: '\e031'; +} + +.oi[data-glyph=chat]:before { + content: '\e032'; +} + +.oi[data-glyph=check]:before { + content: '\e033'; +} + +.oi[data-glyph=chevron-bottom]:before { + content: '\e034'; +} + +.oi[data-glyph=chevron-left]:before { + content: '\e035'; +} + +.oi[data-glyph=chevron-right]:before { + content: '\e036'; +} + +.oi[data-glyph=chevron-top]:before { + content: '\e037'; +} + +.oi[data-glyph=circle-check]:before { + content: '\e038'; +} + +.oi[data-glyph=circle-x]:before { + content: '\e039'; +} + +.oi[data-glyph=clipboard]:before { + content: '\e03a'; +} + +.oi[data-glyph=clock]:before { + content: '\e03b'; +} + +.oi[data-glyph=cloud-download]:before { + content: '\e03c'; +} + +.oi[data-glyph=cloud-upload]:before { + content: '\e03d'; +} + +.oi[data-glyph=cloud]:before { + content: '\e03e'; +} + +.oi[data-glyph=cloudy]:before { + content: '\e03f'; +} + +.oi[data-glyph=code]:before { + content: '\e040'; +} + +.oi[data-glyph=cog]:before { + content: '\e041'; +} + +.oi[data-glyph=collapse-down]:before { + content: '\e042'; +} + +.oi[data-glyph=collapse-left]:before { + content: '\e043'; +} + +.oi[data-glyph=collapse-right]:before { + content: '\e044'; +} + +.oi[data-glyph=collapse-up]:before { + content: '\e045'; +} + +.oi[data-glyph=command]:before { + content: '\e046'; +} + +.oi[data-glyph=comment-square]:before { + content: '\e047'; +} + +.oi[data-glyph=compass]:before { + content: '\e048'; +} + +.oi[data-glyph=contrast]:before { + content: '\e049'; +} + +.oi[data-glyph=copywriting]:before { + content: '\e04a'; +} + +.oi[data-glyph=credit-card]:before { + content: '\e04b'; +} + +.oi[data-glyph=crop]:before { + content: '\e04c'; +} + +.oi[data-glyph=dashboard]:before { + content: '\e04d'; +} + +.oi[data-glyph=data-transfer-download]:before { + content: '\e04e'; +} + +.oi[data-glyph=data-transfer-upload]:before { + content: '\e04f'; +} + +.oi[data-glyph=delete]:before { + content: '\e050'; +} + +.oi[data-glyph=dial]:before { + content: '\e051'; +} + +.oi[data-glyph=document]:before { + content: '\e052'; +} + +.oi[data-glyph=dollar]:before { + content: '\e053'; +} + +.oi[data-glyph=double-quote-sans-left]:before { + content: '\e054'; +} + +.oi[data-glyph=double-quote-sans-right]:before { + content: '\e055'; +} + +.oi[data-glyph=double-quote-serif-left]:before { + content: '\e056'; +} + +.oi[data-glyph=double-quote-serif-right]:before { + content: '\e057'; +} + +.oi[data-glyph=droplet]:before { + content: '\e058'; +} + +.oi[data-glyph=eject]:before { + content: '\e059'; +} + +.oi[data-glyph=elevator]:before { + content: '\e05a'; +} + +.oi[data-glyph=ellipses]:before { + content: '\e05b'; +} + +.oi[data-glyph=envelope-closed]:before { + content: '\e05c'; +} + +.oi[data-glyph=envelope-open]:before { + content: '\e05d'; +} + +.oi[data-glyph=euro]:before { + content: '\e05e'; +} + +.oi[data-glyph=excerpt]:before { + content: '\e05f'; +} + +.oi[data-glyph=expand-down]:before { + content: '\e060'; +} + +.oi[data-glyph=expand-left]:before { + content: '\e061'; +} + +.oi[data-glyph=expand-right]:before { + content: '\e062'; +} + +.oi[data-glyph=expand-up]:before { + content: '\e063'; +} + +.oi[data-glyph=external-link]:before { + content: '\e064'; +} + +.oi[data-glyph=eye]:before { + content: '\e065'; +} + +.oi[data-glyph=eyedropper]:before { + content: '\e066'; +} + +.oi[data-glyph=file]:before { + content: '\e067'; +} + +.oi[data-glyph=fire]:before { + content: '\e068'; +} + +.oi[data-glyph=flag]:before { + content: '\e069'; +} + +.oi[data-glyph=flash]:before { + content: '\e06a'; +} + +.oi[data-glyph=folder]:before { + content: '\e06b'; +} + +.oi[data-glyph=fork]:before { + content: '\e06c'; +} + +.oi[data-glyph=fullscreen-enter]:before { + content: '\e06d'; +} + +.oi[data-glyph=fullscreen-exit]:before { + content: '\e06e'; +} + +.oi[data-glyph=globe]:before { + content: '\e06f'; +} + +.oi[data-glyph=graph]:before { + content: '\e070'; +} + +.oi[data-glyph=grid-four-up]:before { + content: '\e071'; +} + +.oi[data-glyph=grid-three-up]:before { + content: '\e072'; +} + +.oi[data-glyph=grid-two-up]:before { + content: '\e073'; +} + +.oi[data-glyph=hard-drive]:before { + content: '\e074'; +} + +.oi[data-glyph=header]:before { + content: '\e075'; +} + +.oi[data-glyph=headphones]:before { + content: '\e076'; +} + +.oi[data-glyph=heart]:before { + content: '\e077'; +} + +.oi[data-glyph=home]:before { + content: '\e078'; +} + +.oi[data-glyph=image]:before { + content: '\e079'; +} + +.oi[data-glyph=inbox]:before { + content: '\e07a'; +} + +.oi[data-glyph=infinity]:before { + content: '\e07b'; +} + +.oi[data-glyph=info]:before { + content: '\e07c'; +} + +.oi[data-glyph=italic]:before { + content: '\e07d'; +} + +.oi[data-glyph=justify-center]:before { + content: '\e07e'; +} + +.oi[data-glyph=justify-left]:before { + content: '\e07f'; +} + +.oi[data-glyph=justify-right]:before { + content: '\e080'; +} + +.oi[data-glyph=key]:before { + content: '\e081'; +} + +.oi[data-glyph=laptop]:before { + content: '\e082'; +} + +.oi[data-glyph=layers]:before { + content: '\e083'; +} + +.oi[data-glyph=lightbulb]:before { + content: '\e084'; +} + +.oi[data-glyph=link-broken]:before { + content: '\e085'; +} + +.oi[data-glyph=link-intact]:before { + content: '\e086'; +} + +.oi[data-glyph=list-rich]:before { + content: '\e087'; +} + +.oi[data-glyph=list]:before { + content: '\e088'; +} + +.oi[data-glyph=location]:before { + content: '\e089'; +} + +.oi[data-glyph=lock-locked]:before { + content: '\e08a'; +} + +.oi[data-glyph=lock-unlocked]:before { + content: '\e08b'; +} + +.oi[data-glyph=loop-circular]:before { + content: '\e08c'; +} + +.oi[data-glyph=loop-square]:before { + content: '\e08d'; +} + +.oi[data-glyph=loop]:before { + content: '\e08e'; +} + +.oi[data-glyph=magnifying-glass]:before { + content: '\e08f'; +} + +.oi[data-glyph=map-marker]:before { + content: '\e090'; +} + +.oi[data-glyph=map]:before { + content: '\e091'; +} + +.oi[data-glyph=media-pause]:before { + content: '\e092'; +} + +.oi[data-glyph=media-play]:before { + content: '\e093'; +} + +.oi[data-glyph=media-record]:before { + content: '\e094'; +} + +.oi[data-glyph=media-skip-backward]:before { + content: '\e095'; +} + +.oi[data-glyph=media-skip-forward]:before { + content: '\e096'; +} + +.oi[data-glyph=media-step-backward]:before { + content: '\e097'; +} + +.oi[data-glyph=media-step-forward]:before { + content: '\e098'; +} + +.oi[data-glyph=media-stop]:before { + content: '\e099'; +} + +.oi[data-glyph=medical-cross]:before { + content: '\e09a'; +} + +.oi[data-glyph=menu]:before { + content: '\e09b'; +} + +.oi[data-glyph=microphone]:before { + content: '\e09c'; +} + +.oi[data-glyph=minus]:before { + content: '\e09d'; +} + +.oi[data-glyph=monitor]:before { + content: '\e09e'; +} + +.oi[data-glyph=moon]:before { + content: '\e09f'; +} + +.oi[data-glyph=move]:before { + content: '\e0a0'; +} + +.oi[data-glyph=musical-note]:before { + content: '\e0a1'; +} + +.oi[data-glyph=paperclip]:before { + content: '\e0a2'; +} + +.oi[data-glyph=pencil]:before { + content: '\e0a3'; +} + +.oi[data-glyph=people]:before { + content: '\e0a4'; +} + +.oi[data-glyph=person]:before { + content: '\e0a5'; +} + +.oi[data-glyph=phone]:before { + content: '\e0a6'; +} + +.oi[data-glyph=pie-chart]:before { + content: '\e0a7'; +} + +.oi[data-glyph=pin]:before { + content: '\e0a8'; +} + +.oi[data-glyph=play-circle]:before { + content: '\e0a9'; +} + +.oi[data-glyph=plus]:before { + content: '\e0aa'; +} + +.oi[data-glyph=power-standby]:before { + content: '\e0ab'; +} + +.oi[data-glyph=print]:before { + content: '\e0ac'; +} + +.oi[data-glyph=project]:before { + content: '\e0ad'; +} + +.oi[data-glyph=pulse]:before { + content: '\e0ae'; +} + +.oi[data-glyph=puzzle-piece]:before { + content: '\e0af'; +} + +.oi[data-glyph=question-mark]:before { + content: '\e0b0'; +} + +.oi[data-glyph=rain]:before { + content: '\e0b1'; +} + +.oi[data-glyph=random]:before { + content: '\e0b2'; +} + +.oi[data-glyph=reload]:before { + content: '\e0b3'; +} + +.oi[data-glyph=resize-both]:before { + content: '\e0b4'; +} + +.oi[data-glyph=resize-height]:before { + content: '\e0b5'; +} + +.oi[data-glyph=resize-width]:before { + content: '\e0b6'; +} + +.oi[data-glyph=rss-alt]:before { + content: '\e0b7'; +} + +.oi[data-glyph=rss]:before { + content: '\e0b8'; +} + +.oi[data-glyph=script]:before { + content: '\e0b9'; +} + +.oi[data-glyph=share-boxed]:before { + content: '\e0ba'; +} + +.oi[data-glyph=share]:before { + content: '\e0bb'; +} + +.oi[data-glyph=shield]:before { + content: '\e0bc'; +} + +.oi[data-glyph=signal]:before { + content: '\e0bd'; +} + +.oi[data-glyph=signpost]:before { + content: '\e0be'; +} + +.oi[data-glyph=sort-ascending]:before { + content: '\e0bf'; +} + +.oi[data-glyph=sort-descending]:before { + content: '\e0c0'; +} + +.oi[data-glyph=spreadsheet]:before { + content: '\e0c1'; +} + +.oi[data-glyph=star]:before { + content: '\e0c2'; +} + +.oi[data-glyph=sun]:before { + content: '\e0c3'; +} + +.oi[data-glyph=tablet]:before { + content: '\e0c4'; +} + +.oi[data-glyph=tag]:before { + content: '\e0c5'; +} + +.oi[data-glyph=tags]:before { + content: '\e0c6'; +} + +.oi[data-glyph=target]:before { + content: '\e0c7'; +} + +.oi[data-glyph=task]:before { + content: '\e0c8'; +} + +.oi[data-glyph=terminal]:before { + content: '\e0c9'; +} + +.oi[data-glyph=text]:before { + content: '\e0ca'; +} + +.oi[data-glyph=thumb-down]:before { + content: '\e0cb'; +} + +.oi[data-glyph=thumb-up]:before { + content: '\e0cc'; +} + +.oi[data-glyph=timer]:before { + content: '\e0cd'; +} + +.oi[data-glyph=transfer]:before { + content: '\e0ce'; +} + +.oi[data-glyph=trash]:before { + content: '\e0cf'; +} + +.oi[data-glyph=underline]:before { + content: '\e0d0'; +} + +.oi[data-glyph=vertical-align-bottom]:before { + content: '\e0d1'; +} + +.oi[data-glyph=vertical-align-center]:before { + content: '\e0d2'; +} + +.oi[data-glyph=vertical-align-top]:before { + content: '\e0d3'; +} + +.oi[data-glyph=video]:before { + content: '\e0d4'; +} + +.oi[data-glyph=volume-high]:before { + content: '\e0d5'; +} + +.oi[data-glyph=volume-low]:before { + content: '\e0d6'; +} + +.oi[data-glyph=volume-off]:before { + content: '\e0d7'; +} + +.oi[data-glyph=warning]:before { + content: '\e0d8'; +} + +.oi[data-glyph=wifi]:before { + content: '\e0d9'; +} + +.oi[data-glyph=wrench]:before { + content: '\e0da'; +} + +.oi[data-glyph=x]:before { + content: '\e0db'; +} + +.oi[data-glyph=yen]:before { + content: '\e0dc'; +} + +.oi[data-glyph=zoom-in]:before { + content: '\e0dd'; +} + +.oi[data-glyph=zoom-out]:before { + content: '\e0de'; +} + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.styl b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.styl new file mode 100644 index 00000000..f541bc2d --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/css/open-iconic.styl @@ -0,0 +1,733 @@ +@font-face + font-family 'Icons' + src url('../fonts/open-iconic.eot') + src url('../fonts/open-iconic.eot?#iconic-sm') format('embedded-opentype'), url('../fonts/open-iconic.woff') format('woff'), url('../fonts/open-iconic.ttf') format('truetype'), url('../fonts/open-iconic.otf') format('opentype'), url('../fonts/open-iconic.svg#iconic-sm') format('svg') + font-weight normal + font-style normal + + +.oi[data-glyph].oi-text-replace + font-size 0 + line-height 0 + +.oi[data-glyph].oi-text-replace:before + width 1em + text-align center + +.oi[data-glyph] + &:before + position relative + top 1px + font-family 'Icons' + display inline-block + speak none + line-height 1 + vertical-align baseline + font-weight normal + font-style normal + -webkit-font-smoothing antialiased + -moz-osx-font-smoothing grayscale + + &:empty:before + width 1em + text-align center + box-sizing content-box + + &.oi-align-left:before + text-align left + + &.oi-align-right:before + text-align right + + &.oi-align-center:before + text-align center + + + &.oi-flip-horizontal:before + -webkit-transform scale(-1, 1) + -ms-transform scale(-1, 1) + transform scale(-1, 1) + + + &.oi-flip-vertical:before + -webkit-transform scale(1, -1) + -ms-transform scale(-1, 1) + transform scale(1, -1) + + + &.oi-flip-horizontal-vertical:before + -webkit-transform scale(-1, -1) + -ms-transform scale(-1, 1) + transform scale(-1, -1) + + + + +.oi[data-glyph=account-login]:before + content '\e000' + +.oi[data-glyph=account-logout]:before + content '\e001' + +.oi[data-glyph=action-redo]:before + content '\e002' + +.oi[data-glyph=action-undo]:before + content '\e003' + +.oi[data-glyph=align-center]:before + content '\e004' + +.oi[data-glyph=align-left]:before + content '\e005' + +.oi[data-glyph=align-right]:before + content '\e006' + +.oi[data-glyph=aperture]:before + content '\e007' + +.oi[data-glyph=arrow-bottom]:before + content '\e008' + +.oi[data-glyph=arrow-circle-bottom]:before + content '\e009' + +.oi[data-glyph=arrow-circle-left]:before + content '\e00a' + +.oi[data-glyph=arrow-circle-right]:before + content '\e00b' + +.oi[data-glyph=arrow-circle-top]:before + content '\e00c' + +.oi[data-glyph=arrow-left]:before + content '\e00d' + +.oi[data-glyph=arrow-right]:before + content '\e00e' + +.oi[data-glyph=arrow-thick-bottom]:before + content '\e00f' + +.oi[data-glyph=arrow-thick-left]:before + content '\e010' + +.oi[data-glyph=arrow-thick-right]:before + content '\e011' + +.oi[data-glyph=arrow-thick-top]:before + content '\e012' + +.oi[data-glyph=arrow-top]:before + content '\e013' + +.oi[data-glyph=audio-spectrum]:before + content '\e014' + +.oi[data-glyph=audio]:before + content '\e015' + +.oi[data-glyph=badge]:before + content '\e016' + +.oi[data-glyph=ban]:before + content '\e017' + +.oi[data-glyph=bar-chart]:before + content '\e018' + +.oi[data-glyph=basket]:before + content '\e019' + +.oi[data-glyph=battery-empty]:before + content '\e01a' + +.oi[data-glyph=battery-full]:before + content '\e01b' + +.oi[data-glyph=beaker]:before + content '\e01c' + +.oi[data-glyph=bell]:before + content '\e01d' + +.oi[data-glyph=bluetooth]:before + content '\e01e' + +.oi[data-glyph=bold]:before + content '\e01f' + +.oi[data-glyph=bolt]:before + content '\e020' + +.oi[data-glyph=book]:before + content '\e021' + +.oi[data-glyph=bookmark]:before + content '\e022' + +.oi[data-glyph=box]:before + content '\e023' + +.oi[data-glyph=briefcase]:before + content '\e024' + +.oi[data-glyph=british-pound]:before + content '\e025' + +.oi[data-glyph=browser]:before + content '\e026' + +.oi[data-glyph=brush]:before + content '\e027' + +.oi[data-glyph=bug]:before + content '\e028' + +.oi[data-glyph=bullhorn]:before + content '\e029' + +.oi[data-glyph=calculator]:before + content '\e02a' + +.oi[data-glyph=calendar]:before + content '\e02b' + +.oi[data-glyph=camera-slr]:before + content '\e02c' + +.oi[data-glyph=caret-bottom]:before + content '\e02d' + +.oi[data-glyph=caret-left]:before + content '\e02e' + +.oi[data-glyph=caret-right]:before + content '\e02f' + +.oi[data-glyph=caret-top]:before + content '\e030' + +.oi[data-glyph=cart]:before + content '\e031' + +.oi[data-glyph=chat]:before + content '\e032' + +.oi[data-glyph=check]:before + content '\e033' + +.oi[data-glyph=chevron-bottom]:before + content '\e034' + +.oi[data-glyph=chevron-left]:before + content '\e035' + +.oi[data-glyph=chevron-right]:before + content '\e036' + +.oi[data-glyph=chevron-top]:before + content '\e037' + +.oi[data-glyph=circle-check]:before + content '\e038' + +.oi[data-glyph=circle-x]:before + content '\e039' + +.oi[data-glyph=clipboard]:before + content '\e03a' + +.oi[data-glyph=clock]:before + content '\e03b' + +.oi[data-glyph=cloud-download]:before + content '\e03c' + +.oi[data-glyph=cloud-upload]:before + content '\e03d' + +.oi[data-glyph=cloud]:before + content '\e03e' + +.oi[data-glyph=cloudy]:before + content '\e03f' + +.oi[data-glyph=code]:before + content '\e040' + +.oi[data-glyph=cog]:before + content '\e041' + +.oi[data-glyph=collapse-down]:before + content '\e042' + +.oi[data-glyph=collapse-left]:before + content '\e043' + +.oi[data-glyph=collapse-right]:before + content '\e044' + +.oi[data-glyph=collapse-up]:before + content '\e045' + +.oi[data-glyph=command]:before + content '\e046' + +.oi[data-glyph=comment-square]:before + content '\e047' + +.oi[data-glyph=compass]:before + content '\e048' + +.oi[data-glyph=contrast]:before + content '\e049' + +.oi[data-glyph=copywriting]:before + content '\e04a' + +.oi[data-glyph=credit-card]:before + content '\e04b' + +.oi[data-glyph=crop]:before + content '\e04c' + +.oi[data-glyph=dashboard]:before + content '\e04d' + +.oi[data-glyph=data-transfer-download]:before + content '\e04e' + +.oi[data-glyph=data-transfer-upload]:before + content '\e04f' + +.oi[data-glyph=delete]:before + content '\e050' + +.oi[data-glyph=dial]:before + content '\e051' + +.oi[data-glyph=document]:before + content '\e052' + +.oi[data-glyph=dollar]:before + content '\e053' + +.oi[data-glyph=double-quote-sans-left]:before + content '\e054' + +.oi[data-glyph=double-quote-sans-right]:before + content '\e055' + +.oi[data-glyph=double-quote-serif-left]:before + content '\e056' + +.oi[data-glyph=double-quote-serif-right]:before + content '\e057' + +.oi[data-glyph=droplet]:before + content '\e058' + +.oi[data-glyph=eject]:before + content '\e059' + +.oi[data-glyph=elevator]:before + content '\e05a' + +.oi[data-glyph=ellipses]:before + content '\e05b' + +.oi[data-glyph=envelope-closed]:before + content '\e05c' + +.oi[data-glyph=envelope-open]:before + content '\e05d' + +.oi[data-glyph=euro]:before + content '\e05e' + +.oi[data-glyph=excerpt]:before + content '\e05f' + +.oi[data-glyph=expand-down]:before + content '\e060' + +.oi[data-glyph=expand-left]:before + content '\e061' + +.oi[data-glyph=expand-right]:before + content '\e062' + +.oi[data-glyph=expand-up]:before + content '\e063' + +.oi[data-glyph=external-link]:before + content '\e064' + +.oi[data-glyph=eye]:before + content '\e065' + +.oi[data-glyph=eyedropper]:before + content '\e066' + +.oi[data-glyph=file]:before + content '\e067' + +.oi[data-glyph=fire]:before + content '\e068' + +.oi[data-glyph=flag]:before + content '\e069' + +.oi[data-glyph=flash]:before + content '\e06a' + +.oi[data-glyph=folder]:before + content '\e06b' + +.oi[data-glyph=fork]:before + content '\e06c' + +.oi[data-glyph=fullscreen-enter]:before + content '\e06d' + +.oi[data-glyph=fullscreen-exit]:before + content '\e06e' + +.oi[data-glyph=globe]:before + content '\e06f' + +.oi[data-glyph=graph]:before + content '\e070' + +.oi[data-glyph=grid-four-up]:before + content '\e071' + +.oi[data-glyph=grid-three-up]:before + content '\e072' + +.oi[data-glyph=grid-two-up]:before + content '\e073' + +.oi[data-glyph=hard-drive]:before + content '\e074' + +.oi[data-glyph=header]:before + content '\e075' + +.oi[data-glyph=headphones]:before + content '\e076' + +.oi[data-glyph=heart]:before + content '\e077' + +.oi[data-glyph=home]:before + content '\e078' + +.oi[data-glyph=image]:before + content '\e079' + +.oi[data-glyph=inbox]:before + content '\e07a' + +.oi[data-glyph=infinity]:before + content '\e07b' + +.oi[data-glyph=info]:before + content '\e07c' + +.oi[data-glyph=italic]:before + content '\e07d' + +.oi[data-glyph=justify-center]:before + content '\e07e' + +.oi[data-glyph=justify-left]:before + content '\e07f' + +.oi[data-glyph=justify-right]:before + content '\e080' + +.oi[data-glyph=key]:before + content '\e081' + +.oi[data-glyph=laptop]:before + content '\e082' + +.oi[data-glyph=layers]:before + content '\e083' + +.oi[data-glyph=lightbulb]:before + content '\e084' + +.oi[data-glyph=link-broken]:before + content '\e085' + +.oi[data-glyph=link-intact]:before + content '\e086' + +.oi[data-glyph=list-rich]:before + content '\e087' + +.oi[data-glyph=list]:before + content '\e088' + +.oi[data-glyph=location]:before + content '\e089' + +.oi[data-glyph=lock-locked]:before + content '\e08a' + +.oi[data-glyph=lock-unlocked]:before + content '\e08b' + +.oi[data-glyph=loop-circular]:before + content '\e08c' + +.oi[data-glyph=loop-square]:before + content '\e08d' + +.oi[data-glyph=loop]:before + content '\e08e' + +.oi[data-glyph=magnifying-glass]:before + content '\e08f' + +.oi[data-glyph=map-marker]:before + content '\e090' + +.oi[data-glyph=map]:before + content '\e091' + +.oi[data-glyph=media-pause]:before + content '\e092' + +.oi[data-glyph=media-play]:before + content '\e093' + +.oi[data-glyph=media-record]:before + content '\e094' + +.oi[data-glyph=media-skip-backward]:before + content '\e095' + +.oi[data-glyph=media-skip-forward]:before + content '\e096' + +.oi[data-glyph=media-step-backward]:before + content '\e097' + +.oi[data-glyph=media-step-forward]:before + content '\e098' + +.oi[data-glyph=media-stop]:before + content '\e099' + +.oi[data-glyph=medical-cross]:before + content '\e09a' + +.oi[data-glyph=menu]:before + content '\e09b' + +.oi[data-glyph=microphone]:before + content '\e09c' + +.oi[data-glyph=minus]:before + content '\e09d' + +.oi[data-glyph=monitor]:before + content '\e09e' + +.oi[data-glyph=moon]:before + content '\e09f' + +.oi[data-glyph=move]:before + content '\e0a0' + +.oi[data-glyph=musical-note]:before + content '\e0a1' + +.oi[data-glyph=paperclip]:before + content '\e0a2' + +.oi[data-glyph=pencil]:before + content '\e0a3' + +.oi[data-glyph=people]:before + content '\e0a4' + +.oi[data-glyph=person]:before + content '\e0a5' + +.oi[data-glyph=phone]:before + content '\e0a6' + +.oi[data-glyph=pie-chart]:before + content '\e0a7' + +.oi[data-glyph=pin]:before + content '\e0a8' + +.oi[data-glyph=play-circle]:before + content '\e0a9' + +.oi[data-glyph=plus]:before + content '\e0aa' + +.oi[data-glyph=power-standby]:before + content '\e0ab' + +.oi[data-glyph=print]:before + content '\e0ac' + +.oi[data-glyph=project]:before + content '\e0ad' + +.oi[data-glyph=pulse]:before + content '\e0ae' + +.oi[data-glyph=puzzle-piece]:before + content '\e0af' + +.oi[data-glyph=question-mark]:before + content '\e0b0' + +.oi[data-glyph=rain]:before + content '\e0b1' + +.oi[data-glyph=random]:before + content '\e0b2' + +.oi[data-glyph=reload]:before + content '\e0b3' + +.oi[data-glyph=resize-both]:before + content '\e0b4' + +.oi[data-glyph=resize-height]:before + content '\e0b5' + +.oi[data-glyph=resize-width]:before + content '\e0b6' + +.oi[data-glyph=rss-alt]:before + content '\e0b7' + +.oi[data-glyph=rss]:before + content '\e0b8' + +.oi[data-glyph=script]:before + content '\e0b9' + +.oi[data-glyph=share-boxed]:before + content '\e0ba' + +.oi[data-glyph=share]:before + content '\e0bb' + +.oi[data-glyph=shield]:before + content '\e0bc' + +.oi[data-glyph=signal]:before + content '\e0bd' + +.oi[data-glyph=signpost]:before + content '\e0be' + +.oi[data-glyph=sort-ascending]:before + content '\e0bf' + +.oi[data-glyph=sort-descending]:before + content '\e0c0' + +.oi[data-glyph=spreadsheet]:before + content '\e0c1' + +.oi[data-glyph=star]:before + content '\e0c2' + +.oi[data-glyph=sun]:before + content '\e0c3' + +.oi[data-glyph=tablet]:before + content '\e0c4' + +.oi[data-glyph=tag]:before + content '\e0c5' + +.oi[data-glyph=tags]:before + content '\e0c6' + +.oi[data-glyph=target]:before + content '\e0c7' + +.oi[data-glyph=task]:before + content '\e0c8' + +.oi[data-glyph=terminal]:before + content '\e0c9' + +.oi[data-glyph=text]:before + content '\e0ca' + +.oi[data-glyph=thumb-down]:before + content '\e0cb' + +.oi[data-glyph=thumb-up]:before + content '\e0cc' + +.oi[data-glyph=timer]:before + content '\e0cd' + +.oi[data-glyph=transfer]:before + content '\e0ce' + +.oi[data-glyph=trash]:before + content '\e0cf' + +.oi[data-glyph=underline]:before + content '\e0d0' + +.oi[data-glyph=vertical-align-bottom]:before + content '\e0d1' + +.oi[data-glyph=vertical-align-center]:before + content '\e0d2' + +.oi[data-glyph=vertical-align-top]:before + content '\e0d3' + +.oi[data-glyph=video]:before + content '\e0d4' + +.oi[data-glyph=volume-high]:before + content '\e0d5' + +.oi[data-glyph=volume-low]:before + content '\e0d6' + +.oi[data-glyph=volume-off]:before + content '\e0d7' + +.oi[data-glyph=warning]:before + content '\e0d8' + +.oi[data-glyph=wifi]:before + content '\e0d9' + +.oi[data-glyph=wrench]:before + content '\e0da' + +.oi[data-glyph=x]:before + content '\e0db' + +.oi[data-glyph=yen]:before + content '\e0dc' + +.oi[data-glyph=zoom-in]:before + content '\e0dd' + +.oi[data-glyph=zoom-out]:before + content '\e0de' diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.eot b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.eot new file mode 100644 index 00000000..f98177db Binary files /dev/null and b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.eot differ diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.otf b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.otf new file mode 100644 index 00000000..f6bd6846 Binary files /dev/null and b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.otf differ diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.svg b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.svg new file mode 100644 index 00000000..32b2c4e9 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.svg @@ -0,0 +1,543 @@ + + + + + +Created by FontForge 20120731 at Tue Jul 1 20:39:22 2014 + By P.J. Onori +Created by P.J. Onori with FontForge 2.0 (http://fontforge.sf.net) + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.ttf b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.ttf new file mode 100644 index 00000000..fab60486 Binary files /dev/null and b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.ttf differ diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.woff b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.woff new file mode 100644 index 00000000..f9309988 Binary files /dev/null and b/class/RealSpaceInterface/static/fonts/open-iconic/font/fonts/open-iconic.woff differ diff --git a/class/RealSpaceInterface/static/fonts/open-iconic/package.json b/class/RealSpaceInterface/static/fonts/open-iconic/package.json new file mode 100644 index 00000000..d1e76ca0 --- /dev/null +++ b/class/RealSpaceInterface/static/fonts/open-iconic/package.json @@ -0,0 +1,36 @@ +{ + "name": "open-iconic", + "description": "An open source icon set with marks in SVG, sprite, webfont and raster format", + "version": "1.1.1", + "keywords": ["icon", "iconic", "open-iconic", "svg", "sprite", "font", "png", "webp"], + "homepage": "http://useiconic.com/open-iconic/", + "author": { + "name": "Iconic", + "email": "yourfriends@useiconic.com", + "web": "http://useiconic.com/" + }, + "repository": { + "type": "git", + "url": "https://github.com/iconic/open-iconic.git" + }, + "contributors": [ + { + "name": "P.J. Onori", + "web": "http://twitter.com/somerandomdude" + }, + { + "name": "Dave Johnson", + "web": "http://twitter.com/protodave" + } + ], + "licenses": [ + { + "type": "MIT License", + "url": "http://opensource.org/licenses/mit-license.html" + }, + { + "type": "SIL OFL 1.1", + "url": "http://scripts.sil.org/OFL" + } + ] +} diff --git a/class/RealSpaceInterface/static/images/cmap.png b/class/RealSpaceInterface/static/images/cmap.png new file mode 100644 index 00000000..68d1ec8c Binary files /dev/null and b/class/RealSpaceInterface/static/images/cmap.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Default/default.png b/class/RealSpaceInterface/static/images/colormaps/Default/default.png new file mode 100644 index 00000000..fe8479ee Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Default/default.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Diverging/RdYlBu.png b/class/RealSpaceInterface/static/images/colormaps/Diverging/RdYlBu.png new file mode 100644 index 00000000..f8f5529b Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Diverging/RdYlBu.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Diverging/Spectral.png b/class/RealSpaceInterface/static/images/colormaps/Diverging/Spectral.png new file mode 100644 index 00000000..180960f1 Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Diverging/Spectral.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Diverging/seismic.png b/class/RealSpaceInterface/static/images/colormaps/Diverging/seismic.png new file mode 100644 index 00000000..54c3eb10 Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Diverging/seismic.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Miscellaneous/jet.png b/class/RealSpaceInterface/static/images/colormaps/Miscellaneous/jet.png new file mode 100644 index 00000000..ed2a5134 Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Miscellaneous/jet.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Uniform/inferno.png b/class/RealSpaceInterface/static/images/colormaps/Uniform/inferno.png new file mode 100644 index 00000000..5eaae181 Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Uniform/inferno.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Uniform/magma.png b/class/RealSpaceInterface/static/images/colormaps/Uniform/magma.png new file mode 100644 index 00000000..63502da8 Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Uniform/magma.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Uniform/plasma.png b/class/RealSpaceInterface/static/images/colormaps/Uniform/plasma.png new file mode 100644 index 00000000..90d8bd30 Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Uniform/plasma.png differ diff --git a/class/RealSpaceInterface/static/images/colormaps/Uniform/viridis.png b/class/RealSpaceInterface/static/images/colormaps/Uniform/viridis.png new file mode 100644 index 00000000..68d1ec8c Binary files /dev/null and b/class/RealSpaceInterface/static/images/colormaps/Uniform/viridis.png differ diff --git a/class/RealSpaceInterface/static/js/.Rhistory b/class/RealSpaceInterface/static/js/.Rhistory new file mode 100644 index 00000000..e69de29b diff --git a/class/RealSpaceInterface/static/js/RSI.js b/class/RealSpaceInterface/static/js/RSI.js new file mode 100644 index 00000000..2fcc5408 --- /dev/null +++ b/class/RealSpaceInterface/static/js/RSI.js @@ -0,0 +1,1756 @@ +/** @module RSI */ + +/** + * Display a warning message if web browser does not support WebGL. + */ +if (!Detector.webgl) { + Detector.addGetWebGLMessage(); + document.getElementById('container').innerHTML = ""; +} + +////////////////////// +// Global Variables // +////////////////////// + +/** + * Indicates whether initial condition has been set. + * @type {boolean} + */ +var initialSet = false; //initialConditions are not set +/** + * Indicates whether cosmological parameters have been set. + * @type {boolean} + */ +var cosmoSet = false; //cosmological parameters are not set +/** + * indicates whether calculation is running (i.e. initial or cosmological) + * @type {boolean} + */ +var calculationRunning = false; +/** + * indicates whether initial state has been received. + * @type {boolean} + */ +var receivedInitial = false; + +/** + * array containing redshift values. + * @type {number[]} + */ +var redshift = ["Initial"]; +/** + * True if simulation is to be run until today, else until decoupling. + * @type {boolean} + */ +var stopAtDecoupling = true; +/** + * The last frame (inclusive) to be displayed when simulation is run until decoupling. + * @type {number} + */ +var decouplingFrame = 0; + +/** + * Active quantity. Must be from {@link QUANTITIES}. + * + * @type {string} + */ +var activeQuantity = "d_g"; + +var container, stats; + +/** + * @type {THREE.Camera} + */ +var camera; +/** + * @type {THREE.Scene} + */ +var scene; +/** + * @type {THREE.OrbitControls} + */ +var controls; +/** + * @type {THREE.WebGLRenderer} + */ +var renderer; + +/** + * @type {THREE.Clock} + */ +var clock = new THREE.Clock(); + +/** + * Size of grid divisions. + * Set in {@link module:RSI~onInitialConditionSet}. + * @type {string} + */ +var realScale = "0 Mpc"; + +/* + * @type {SimulationManager} + */ +var simulationManager; + +/** + * List of color map objects: + *

+ * [{name: <name>, texture: <texture>}, ...]
+ * 
+ *
+ * @type {Array.>}
+ * */
+var colorMaps = [];
+
+/**
+ * GUI responsible for controlling inital + cosmological parameters.
+ * @type {module:paramGui~ParamGui}
+ */
+var parameterGui;
+
+/**
+ * modal dialog containing table of previous simulations and
+ * their previous parameters.
+ *
+ * @type {SimuTable}
+ * @see {SimuTable}
+ */
+var simuTable;
+
+/**
+ * Player controls.
+ *
+ * @type {PlayerPanel}
+ */
+var playerPanel;
+
+/**
+ * flot.js instance for transfer function plot.
+ */
+var transferFunctionPlot;
+
+/**
+ * flot.js instance for Cl plot.
+ */
+var tClPlot;
+
+/**
+ * Indicates whether plots panel is visible.
+ * @type {boolean}
+ */
+var plotWindowVisible = true;
+
+/**
+ * Holds the list of k's for the transfer function plot.
+ * @type {number[]}
+ */
+var kRange;
+
+/**
+ * Indicates whether websocket connection is closed.
+ * @type {boolean}
+ */
+var closed = true;
+/**
+ * Current frame.
+ * @type {number}
+ */
+var frame = 0;
+/**
+ * Indicates whether animation is currently running.
+ * @ŧype {boolean}
+ */
+var animationRunning = false;
+
+/**
+ * Field of View (in degrees) of perspective camera
+ * @type {number}
+ */
+var FoV = 45;
+
+/**
+ * true if scene is to be rendered using an orthographic camera.
+ * @type {boolean}
+ * @see {@link module:RSI~toggleCameraMode}
+ */
+var orthographicMode = false;
+
+/**
+ * Renderer used to create images / .gifs.
+ * @type {THREE.WebGLRenderer}
+ */
+var imgRenderer = new THREE.WebGLRenderer();
+
+/**
+ * Orthographic camera used for image / .gif creation.
+ * @type {THREE.OrthographicCamera}
+ */
+var orthoCam;
+
+/**
+ * Number of decimal digits to round redshift values to.
+ * @type {number}
+ */
+var REDSHIFT_ROUND = 1;
+
+/**
+ * List of visually distinct colors for use in plots,
+ * taken from {@link https://sashat.me/2017/01/11/list-of-20-simple-distinct-colors/}
+ */
+var colors = [
+    "#e6194b",
+    "#3cb44b",
+    // "#ffe119", // yellow, hard to see on white ground
+    "#0082c8",
+    "#f58231",
+    "#911eb4",
+    // "#46f0f0", // cyan, hard to see on white ground
+    "#f032e6",
+    "#d2f53c",
+    "#fabebe",
+    "#008080",
+    "#e6beff",
+    "#aa6e28",
+    "#fffac8",
+    "#800000",
+    "#aaffc3",
+    "#808000",
+    "#ffd8b1",
+    "#000080",
+    "#808080",
+    "#FFFFFF",
+    "#000000"
+];
+
+/**
+ * Plot options for Cl's
+ */
+var tClPlotOptions = {
+    legend: {
+        show: false,
+    },
+    xaxis: {
+        axisLabel: "ℓ",
+        // transform: Math.log,
+        // inverseTransform: Math.exp,
+    },
+    yaxis: {
+        tickFormatter: function(num, obj) {
+            if (num > 0 && num < 1e-3) {
+                var power = Math.floor(Math.log10(num));
+                var prefix = num / Math.pow(10, power);
+                return round(prefix, 2) + "·10" + power + "";
+            }
+            return num;
+        },
+        axisLabel: "ℓ (ℓ+1) CTT / (2π)",
+    },
+};
+
+/**
+ * Plot options for matter spectrum
+ */
+var mPkPlotOptions = {
+    legend: {
+        show: false,
+    },
+    xaxis: {
+        transform: Math.log,
+        inverseTransform: Math.exp,
+        axisLabel: "k [h/Mpc]",
+        ticks: [[1e-3, "10-3"], [1e-2, "10-2"], [1e-1, "10-1"], 1, 10],
+    },
+    yaxis: {
+        transform: Math.log,
+        inverseTransform: Math.exp,
+        tickFormatter: function(num, obj) {
+            var power = Math.floor(Math.log10(num));
+            var prefix = num / Math.pow(10, power);
+            var result = "";
+            if (prefix != 1)
+                result += round(prefix, 2) + "·";
+            return result + "10" + power + "";
+        },
+        axisLabel: "P(k) [(Mpc/h)3]",
+        ticks: [1, 10, 100, 1000, 10000, 100000, 1000000],
+        min: 0.1,
+    },
+};
+
+/**
+ * Plot options for transfer function(s)
+ */
+var transferPlotOptions = {
+    legend: {
+        show: false,
+    },
+    xaxis: {
+        axisLabel: "k [Mpc-1]",
+        transform: Math.log,
+        inverseTransform: Math.exp,
+        ticks: [[1e-3, "10-3"], [1e-2, "10-2"], [1e-1, "10-1"], 1],
+    },
+    yaxis: {
+        axisLabel: "transfer function",
+        min: -5,
+        max: 5,
+    },
+};
+
+
+/**
+ * Raycaster for mouse picking
+ * @type {THREE.Raycaster}
+ */
+var raycaster = new THREE.Raycaster();
+/**
+ * 2d vector containing mouse position.
+ * @type {THREE.Vector2}
+ */
+var mouse = new THREE.Vector2();
+
+
+/* ENTRY POINT */
+$(document).ready(connect);
+
+/**
+ * Mouse Event Callback which is called on every mouse move.
+ * It is required to track the mouse's position since it's required
+ * to feed its position to the raycaster to determine over which mesh
+ * the mouse is currently hovering.
+ */
+function onMouseMove(ev) {
+    var rect = container.getBoundingClientRect();
+    mouse.x = ((ev.clientX - rect.left) / window.innerWidth) * 2 - 1;
+    mouse.y = -((ev.clientY - rect.top) / window.innerHeight) * 2 + 1;
+}
+
+
+/**
+ * Once the websocket in {@link module:RSI~connect} has established a connection,
+ * this function will be called, which initializes the application.
+ */
+function start() {
+    init();
+    step();
+    requestAnimationFrame(animate);
+}
+
+/**
+ * Logging function
+ *
+ * @param {Object} msg
+ */
+function log(msg) {
+    console.log("D: " + msg);
+}
+
+/**
+ * Entry point for the whole application.
+ *
+ * Establishes a connection to the WebSocket provided by the backend.
+ */
+function connect() {
+    // connection = new SockJS('http://' + window.location.host + '/datasocket');
+    connection = new WebSocket("ws://" + window.location.host + "/datasocket");
+
+    log("Connecting...");
+
+    connection.onopen = function() {
+        log("Connected!");
+        start();
+    };
+
+    connection.onmessage = messageCallback;
+
+    connection.onclose = function() {
+        log('Disconnected.');
+        connection = null;
+        onClose();
+    };
+}
+
+/**
+ * Message callback for the WebSocket connection which gets called for each
+ * received message.
+ *
+ * @param {Object} e - message event object
+ */
+function messageCallback(e) {
+    var message = JSON.parse(e.data);
+    /**
+     * Once data has been received, update the progress in the progress
+     * in the progress modal and call {@link module:RSI~onData} to process
+     * the received data.
+     * Also, flag {@link receivedInitial} as true if no initial data has been
+     * received prior.
+     */
+    if (message.type == 'data') {
+        if (message.hasOwnProperty("progress")) {
+            var percentage = (message.progress * 100).toFixed(1) + "%";
+            $("#simulationProgressBar").css({width: percentage});
+            $("#simulationProgressBar").text(percentage);
+        }
+        onData(message, !receivedInitial);
+        if (!receivedInitial) {
+            receivedInitial = true;
+        }
+    /**
+     * The server sends a list of k values (at which the transfer function is sampled)
+     * immediately after the client connected.
+     */
+    } else if (message.type === 'krange') {
+        log("Received k range from server.");
+        kRange = message.k;
+    }
+    /**
+     * Handles the temperature Cl's sent by the server.
+     * The Cl's (and l's) sent by the server conventionally do not contain the samples for l = 0 and l = 1.
+     * They are, however, not already in the conventional form of l * (l + 1) Cl / (2 * Pi),
+     * so they are processed below.
+     * After that, they are added to the active simulation exposed by
+     * {@link SimulationManager#getTarget}.
+     */
+    else if (message.type === "Cl") {
+        log("Received Cl's from server.");
+        var l = message.l;
+        var tCl = message.tCl;
+
+        message.tCl = l.map(function(ll, i) { return tCl[i] * ll * (ll + 1) / (2 * Math.PI); });
+        simulationManager.getTarget().Cls = message;
+    }
+    /**
+     * Handles matter power spectrum, similar to Cl's above.
+     */
+    else if (message.type == "mPk") {
+        log("Received matter spectrum from server");
+        var kh = message.kh;
+        var Pkh = message.Pkh;
+
+        simulationManager.getTarget().mPk = message;
+        plotStaticIfVisible();
+    }
+    /**
+     * The server signals end of calculations or data transfers via a "success" message
+     * of one of several types.
+     * Upon reception of that message the activity indicator is hidden.
+     */
+    else if (message.type == "success") {
+        calculationRunning = false;
+        hideActivityIndicator();
+
+        if (message.sort == 'Initial') {
+            initialSet = true;
+            loadFrame(0);
+        }
+        /**
+         * Once the server has confirmed that it has received cosmological parameters,
+         * immediately request the simulation results.
+         */
+        else if (message.sort == 'Cosmo') {
+            cosmoSet = true;
+            $("#simulationProgressInfo").text("Receiving simulation data...");
+            requestSimulationData();
+        }
+        /**
+         * Handle the server signaling end of data transfer (for all frames).
+         * The progress modal is hidden, and the list of simulations is rebuild from scratch.
+         * Also, the current frame is reloaded to display the newly received data
+         * at the currently active frame.
+         */
+        else if (message.sort == "Data") {
+            log("Success receiving simulation.");
+            $("#simulationProgressModal").modal("hide");
+            simulationManager.finalizeTarget();
+            // Update the simulation list/table
+            simuTable.clear();
+            var simulations = simulationManager.getSimulations();
+            var active = simulationManager.getActive();
+            simuTable.populate(simulationManager.getSimulations(), simulationManager.getActive());
+            loadFrame(frame, true);
+        }
+    }
+    /**
+     * Server sends redshifts immediately after sending initial condition data.
+     */
+    else if (message.type == "redshift") {
+        redshift = ["Initial"].concat(message.redshift);
+    }
+    /**
+     * Server also sends exact z of decoupling extracted from CLASS's background parameters.
+     * Also contains the index of the closest frame *before* decoupling, which this
+     * application requires to stop the simulation playback at the appropriate frame.
+     */
+    else if (message.type == 'decoupling') {
+        log("Decoupling at z = " + message.z + " (frame #" + message.frame + ")");
+        // Add +1 because redshift[0] === "Initial"
+        decouplingFrame = message.frame + 1;
+    }
+    /**
+     * The server notifies the client about the resolution (i.e. the side length of the square
+     * data matrix) it is about to receive.
+     * This is done before an initial state is sent.
+     */
+    else if (message.type == "resolution") {
+        log("Setting resolution to " + message.value);
+        simulationManager.setResolution(message.value);
+    }
+    /**
+     * Currently unused.
+     */
+    else if (message.type == "extrema") {
+    }
+    /**
+     * In case of an exception occuring on the server side, the client is notified of that
+     * and displays the transmitted stack trace to the user.
+     * Also, if one exists, the target simulation (the one, which is currently receiving data)
+     * is destroyed in case of an exception, to guarantee the continued functionality of the
+     * application.
+     */
+    else if (message.type == "exception") {
+        $("#exceptionModalMessage").text(message.exception);
+        if (calculationRunning) {
+            $("#simulationProgressModal").modal("hide");
+            calculationRunning = false;
+        }
+        simulationManager.destroyTarget();
+        $("#exceptionModal").modal("show");
+    }
+}
+
+function sendParams(params,type) {
+    connection.send(JSON.stringify({type:type,params:params}));
+}
+
+/**
+ * Disconnect from the server.
+ */
+function disconnect() {
+    log("disconnecting");
+    connection.close();
+    connection = null;
+}
+
+
+/**
+ * Requests the transfer of the actual data (for all the redshifts) from the server.
+ */
+function requestSimulationData() {
+    log("Requesting calculation result from server...");
+    if (!calculationRunning) {
+        connection.send(JSON.stringify({
+            type: "Start",
+            params: [],
+        }));
+        calculationRunning = true;
+        showActivityIndicator();
+    }
+}
+
+/**
+ * A simple rounding implementation since JavaScript doesn't provide a built-in
+ * solution.
+ * This will round the given number to a maximum number of decimal places (no trailing zeros).
+ *
+ * @param {number} num - The number to round
+ * @param {number} decimalPlaces - Maximum number of decimal places
+ * @return {number} rounding result
+ */
+function round(num, decimalPlaces) {
+    return num.toFixed(decimalPlaces).replace(/(\.)?0+$/, "");
+}
+
+/**
+ * Since the data transfer between server and client (in that direction) is the main
+ * bottleneck of the application, the data is mostly (except for plots, redshifts, ...)
+ * encoded in base64.
+ * This function serves the purpose of decing that data.
+ * The data is assumed to consist of 32-bit floats. Other data formats (e.g. 64-bit floats)
+ * would require a modification of this function.
+ *
+ * @param {string} b64 - base64 encoded data received from the server
+ * @return {Float32Array} The decoded data array
+ */
+function b64ToFloatArray(b64) {
+    var binary = window.atob(b64);
+    var dv = new DataView(new ArrayBuffer(4));
+    var resultLength = binary.length / 4;
+    var result = new Float32Array(resultLength);
+
+    for (var i = 0; i < resultLength; i++) {
+        var idx = 4 * i;
+        for (var offset = 0; offset < 4; offset++) {
+            dv.setUint8(offset, binary.charCodeAt(idx + offset));
+        }
+        result[i] = dv.getFloat32(0, true);
+    }
+
+    return result;
+}
+
+/**
+ * A data array (for a single frame) sent by the server has the following structure:
+ * 

+ * {
+ *  'd_g': <base64 encoded string>,
+ *  'd_b': <base64 encoded string>,
+ *  ...
+ * }
+ * 
+ * Hence, each field must be decoded individually, + * which is done using {@link module:RSI~b64ToFloatArray}. + * + *

+ * {
+ *  'd_g': <Float32Array>,
+ *  'd_b': <Float32Array>,
+ *  ...
+ * }
+ * 
+ * @param {Object} obj - base64 object as described above + * @return {Object} decoded object, as described above + */ +function decodeArray(obj) { + return Object.keys(obj).reduce(function(acc, key) { + acc[key] = b64ToFloatArray(obj[key]); + return acc; + }, {}); +} + +/** + * Toggles the camera mode between an orthographic and a perspective camera + */ +function toggleCameraMode() { + var aspect = $("#container").width() / $("#container").height(); + if (orthographicMode) { + console.log("Switching to perspective mode"); + camera = new THREE.PerspectiveCamera(FoV, aspect, 0.1, 10000); + controls.object = camera; + } + else { + console.log("Switching to orthographic mode"); + camera = new THREE.OrthographicCamera( + -500 * aspect, 500 * aspect, + 500, -500, + -10000, 10000 + ); + controls.object = camera; + } + + orthographicMode = !orthographicMode; +} + +/** + * Switches to so-called 'single mode', which, instead of displaying one quantity + * for multiple simulations side by side, displays all quantities for a + * single simulation side by side. + * In order to enter single mode, following steps will occur in this function: + *
    + *
  1. Enable single mode in the {@link SimulationManager} instance
  2. + *
  3. Remove the 'normal' plane group from the scene
  4. + *
  5. Add the single plane group to the scene
  6. + *
  7. Adapt the top navigation bar, i.e. add a return button and remove quantity selector
  8. + *
  9. Replot
  10. + *
+ * + * @param {number} simulationIndex - the index of the simulation to display in single mode + */ +function enterSingleMode(simulationIndex) { + console.assert(simulationIndex >= 0); + console.assert(simulationIndex < simulationManager.getSimulations().length); + + simulationManager.enableSingleMode(simulationIndex); + scene.remove(simulationManager.getGroup()); + scene.add(simulationManager.getSingleGroup()); + $("#exitSingleMode").show(); + $("#quantityDropdownWrapper").hide(); + $("#simulationListButton").hide(); + + plotTransferFunction(frame); + plotStatic(); +} + +/** + * The opposite of {@link module:RSI~enterSingleMode}. + * In order to exit single mode, following steps will occur in this function: + *
    + *
  1. Disable single mode in the {@link SimulationManager} instance
  2. + *
  3. Remove the single plane group from the scene
  4. + *
  5. Add the 'normal' plane group to the scene
  6. + *
  7. Adapt the top navigation bar back to its original state
  8. + *
  9. Replot
  10. + *
+ */ +function exitSingleMode() { + simulationManager.disableSingleMode(); + scene.remove(simulationManager.getSingleGroup()); + scene.add(simulationManager.getGroup()); + $("#exitSingleMode").hide(); + $("#quantityDropdownWrapper").show(); + $("#simulationListButton").show(); + + plotStatic(); + loadFrame(frame, true); +} + +/** + * Once data is received, this method is called. + * This function is responsible for decoding the received data using + * {@link module:RSI~b64ToFloatArray} and store the result using the + * {@link SimulationManager} instance. + * + * @param {Object} data - A data object as described in {@link module:RSI~b64ToFloatArray} + * @param {bool} initial - true if initial data, false otherwise + */ +function onData(data, initial) { + /** + * If initial data, store it in the simulationManager (instead of simulationManager.getTarget() + * as below in the else branch) and create new Simulation instance using simulationManager + */ + if (initial) { + var realArray = b64ToFloatArray(data.real); + var transferArray = b64ToFloatArray(data.transfer); + var fourierArray = new Float32Array(data.fourier); + + simulationManager.realInit = realArray; + simulationManager.transferInit = transferArray; + simulationManager.fourierInit = fourierArray; + + simulationManager.createSimulation(); + } else { + simulationManager.getTarget().addFrame( + decodeArray(data.real), + decodeArray(data.transfer), + decodeArray(data.fourier) + ); + } +} + + +/** + * Render an image of the specified simulation at a resolution specified by size. + * + * @param {number} simulationIndex - the index (with respect to the simulations array stored + * in the {@link SimulationManager} instance) of the simulation of which to render an image + * @param {number} size - side length in pixels of the image to render + * + * @return {Object} Canvas DOM element + */ +function renderImage(simulationIndex, size) { + var simulation = simulationManager.getSimulations()[simulationIndex]; + console.assert(simulation); + console.assert(simulation.mesh); + + var size = simulationManager.PLANE_SIZE / 2; + orthoCam = new THREE.OrthographicCamera(-size, size, size, -size, 0, 1000); + orthoCam.position.copy(simulation.mesh.position); + orthoCam.position.y = 500; // Lift camera above mesh + orthoCam.lookAt(simulation.mesh.position); + + imgRenderer.setSize(size, size); + imgRenderer.render(scene, orthoCam); + + // var image = new Image(); + // image.src = imgRenderer.domElement.toDataURL(); + + return imgRenderer.domElement; +} + +/** + * @callback gifProgressCallback + * @param {number} frame - number of currently rendered frame + * @param {number} frameCount - total number of all frames (rendered + not yet rendered) + */ + +/** + * @callback gifFinishCallback + * @param {blob} blob - blob of .gif + */ + +/** + * Renders a .gif of the specified simulation. + * + * @param {number} simulationIndex - the index (with respect to the simulations array stored + * in the {@link SimulationManager} instance) of the simulation of which to render the .gif + * @param {number} size - side length in pixels of the .gif to render + * @param {number} fps - frames per second + * @param {number} quality - quality of resulting .gif, corresponds to pixel sampling interval. + * Lower values are better, but also produce bigger files. + * @param {module:RSI~gifProgressCallback} progressCallback - progress callback + * @param {module:RSI~gifFinishCallback} finishCallback - finish callback + */ +function renderGIF(simulationIndex, size, fps, quality, progressCallback, finishCallback) { + var gif = new GIF({ + workers: 2, + quality: quality, + workerScript: "/static/js/gif.worker.js", + }); + + var previousFrame = frame; + + var frameCount = getLastFrame() + 1; + var delay = 1000.0 / fps; + + for (var i = 0; i < frameCount; ++i) { + loadFrame(i); + gif.addFrame(renderImage(simulationIndex, size), { + copy: true, + delay: delay + }); + if (progressCallback) { + progressCallback(i, frameCount); + } + } + progressCallback(frameCount, frameCount); + + if (finishCallback) { + gif.on('finished', finishCallback); + } + + gif.render(); + + loadFrame(previousFrame); +} + + +/** + * Gets called on close / loss of connection and displays a corresponding message to the user. + */ +function onClose() { + closed = true; + alert("Connection to server lost; Reload page to start a new session."); +} + +/** + * Initializes the quantity dropdown by assigning an event handler, which + * updates the currently active quantity and reloads the current frame in order + * for the change to take effect. + */ +function initQuantityDropdown() { + var dropDown = $("#quantity-dropdown"); + dropDown.children().click(function(e) { + dropDown.find(".active").removeClass("active"); + $(this).addClass("active"); + $("#quantity-dropdown-btn").html($(this).html()); + activeQuantity = $(this).attr("data-quantity"); + loadFrame(frame, true); + + e.preventDefault(); + }); +} + +/** + * Initializes the dropup color map selector by assigning an event listener + * which loads the appropriate texture using {@link SimulationManager#setColorMap}. + */ +function initColorMapDropdown() { + var menu = $("#colormap-selector-menu"); + menu.find(".colormap-selector-item").click(function(e) { + menu.find(".colormap-selector-item.active").removeClass("active"); + $(this).addClass("active"); + $("#colormap-selector-button") .css({ + "background": "url(" + $(this).find("img").attr("src") + ")", + "background-size": "contain" + }); + + var texture = new THREE.Texture($(this).find("img").get(0)); + texture.needsUpdate = true; + simulationManager.setColorMap(texture); + + e.preventDefault(); + }); + + menu.find(":contains(default)").click(); +} + +/** + * Initializes the checkbox which toggles between stopping the playback + * at decoupling and today. + */ +function initRedshiftEndToggle() { + $("#redshift-end-toggle").change(function(e) { + stopAtDecoupling = !$(this).get(0).checked; + console.log("Stop at decoupling? " + stopAtDecoupling); + var lastFrame = getLastFrame(); + if (frame > lastFrame) { + loadFrame(lastFrame); + } + updateTimeline(lastFrame); + }); +} + +/** + * Initializes the .gif creation dialog + */ +function initGifDialog() { + log("Initializing .gif dialog"); + var modal = $("#gifExportModal"); + modal.on("show.bs.modal", function() { + $(this).find("#gifExportProgressContainer").hide(); + $(this).find("#gifExportResultContainer").hide(); + }); + $("#gifExportCreateBtn").click(function() { + onCreateGif(modal.data("simulationIndex")); + }); +} + +/** + * Initializes the image creation dialog + */ +function initImgDialog() { + var modal = $("#imgExportModal"); + modal.on("show.bs.modal", function() { + $(this).find("#imgExportResultContainer").hide(); + }); + $("#imgExportCreateBtn").click(function() { + $("#imgExportResultContainer").show(); + + // Hide grids if necessary + var gridShown = parameterGui.config.showGrid; + parameterGui.config.showGrid = $("#imgExportGrid").is(":checked"); + simulationManager.updateGrids(); + + var canvas = renderImage(modal.data("simulationIndex"), $("#imgExportSize").val()); + $("#imgExportResultImage").attr("src", canvas.toDataURL()); + + // Re-show grids if necessary + parameterGui.config.showGrid = gridShown; + simulationManager.updateGrids(); + }); +} + +/** + * Callback function which is called from the {@link SimulationList} instance once + * the user presses the 'Create .gif' button there. + * + * @param {number} simulationIndex - index of simulation to render as .gif + */ +function onCreateGif(simulationIndex) { + log("Creating gif for simulation #" + simulationIndex); + var size = $("#gifExportSize").val(); + var fps = $("#gifExportFPS").val(); + parameterGui.config.showGrid = $("#gifExportGrid").is(":checked"); + simulationManager.updateGrids(); + + var quality = $("#gifExportQuality").val(); + + $("#gifExportProgressContainer").show(); + $("#gifExportResultContainer").hide(); + + renderGIF(simulationIndex, size, fps, quality, gifProgressCallback, gifFinishCallback); +} + +/** + * Implements {@link module:RSI~gifProgressCallback} and is called after every frame + * rendered to the .gif. + * Uses this data to update the progress bar in the .gif creation dialog. + * + * @param {number} frame - number of currently rendered frame + * @param {number} frameCount - total number of all frames (rendered + not yet rendered) + */ +function gifProgressCallback(frame, frameCount) { + var progressPercent = Math.floor(frame / frameCount * 100) + "%"; + $("#gifExportProgressBar").css({width: progressPercent}); + if (frame == frameCount) { + $("#gifExportProgressBar").html("Finalizing .gif…"); + } else { + $("#gifExportProgressBar").text("Rendering Frame " + frame + "/" + frameCount); + } + +} + +/** + * Implements {@link module:RSI~gifFinishCallback} and is called once the .gif has been rendered. + * Proceeds to reset the progress bar in the .gif creation dialog and displays the resulting + * .gif. + * + * @param {blob} blob - data blob of .gif + */ +function gifFinishCallback(blob) { + $("#gifExportProgressBar") .css({width: 0}) + $("#gifExportProgressContainer").hide(); + $("#gifExportResultContainer").show(); + $("#gifExportResultImage").attr("src", URL.createObjectURL(blob)); + $("#gifExportResultMessage").alert(); +} + +/** + * Toggles the visibility of the plot panel. + */ +function togglePlotWindow() { + plotWindowVisible = !plotWindowVisible; + $("#plotWindowWrapper").toggleClass("plotWindowWrapperVisible").toggleClass("plotWindowWrapperHidden"); + $("#plotWindowWrapper").find("div").toggleClass("plotWindowVisible").toggleClass("plotWindowHidden"); + $("#plotWindowToggleIcon").toggleClass("oi-caret-top").toggleClass("oi-caret-bottom"); + + if (plotWindowVisible) { + if (simulationManager.getActive().length == 0) { + initClPlot(); + initTransferPlot(); + } else { + plotStatic(); + plotTransferFunction(frame, true); + } + } +} + +/** + * Initializes the button used to collapse the plot panel. + */ +function initPlotCollapseButton() { + $("#plotWindowToggle").click(function(e) { + togglePlotWindow(); + }); +} + + +/* SECTION: PLOT INITIALIZATION */ + +/** + * Initialize transfer function plot. + */ +function initTransferPlot() { + var initialOptions = Object.assign({}, transferPlotOptions); + initialOptions.xaxis.min = 1e-4; + initialOptions.xaxis.max = 10; + transferFunctionPlot = $.plot($("#transferFunctionPlot"), [{shadowSize: 0, color: colors[0], data: []}], initialOptions); +} + +/** + * Initialize Cl's plot. + */ +function initClPlot() { + var initialOptions = Object.assign({}, tClPlotOptions); + initialOptions.xaxis.min = 2; + initialOptions.xaxis.max = 2500; + $.plot($("#tClPlot"), [{shadowSize: 0, color: colors[0], data: []}], initialOptions); +} + +/** + * Initialize matter spectrum plot. + */ +function initmPkPlot() { + var initialOptions = Object.assign({}, mPkPlotOptions); + initialOptions.xaxis.min = 1e-3; + initialOptions.xaxis.max = 10; + $.plot($("#mPkPlot"), [{shadowSize: 0, data: []}], initialOptions); +} +/* END OF PLOT INITIALIZATION */ + +/** + * Callback to be called once cosmological parameters have been set + * @callback cosmologicalParametersSetCallback + * @param {module:paramGui~CosmoParams} cosmoParamsInstance + * @param {Object} serializedMessage - message to be sent to the server +*/ + +/** + * Callback to be called once initial condition has been set + * @callback initialConditionSetCallback + * @param {module:paramGui~ParamSet} paramSet +*/ + +/** + * Called once user presses button to generate initial state. + * Obtains the JSON representation and sends it to the server. + * Since it isn't particularly enlightening to compare simulations (resulting from different + * cosmological parameters) for different initial state seeds, this also cleans up + * any existing simulations. + * + * @param {module:paramGui~ParamSet} paramSet - initial condition parameter set + */ +function onInitialConditionSet(paramSet) { + if (!calculationRunning) { + if (simulationManager.singleMode) { + exitSingleMode(); + } + log("Sending initial parameters to server."); + var serializedParamSet = paramSet.serializeInitial(); + var paramString = JSON.stringify(serializedParamSet); + log(paramString); + calculationRunning = true; + showActivityIndicator(); + connection.send(paramString); + + simulationManager.deleteAll(); + simuTable.clear(); + + var realScale = serializedParamSet.params.xScale / simulationManager.GRID_DIVISIONS; + $("#displayRealScale").text(round(realScale, 1) + " Mpc"); + + receivedInitial = false; + } +} + +/** + * Called once the user presses the button which sets the cosmological parameters. + *
+ * Implements {@link module:RSI~cosmologicalParametersSetCallback}. + *
+ * If an initial condition has been set, the following steps will occur: + * First, this function checks using {@link SimulationManager~wasAlreadySimulated} + * whether a simulation set for that particular set of cosmological parameters has already + * been computed. + * If so, a message indicating that will be displayed. + * If not, the parameters (which have already been encoded in the appropriate structure + * by {@link module:paramGui~CosmoParams}) will be sent to the server and the progress + * modal will be displayed. + * Also, a new simulation will be created and a copy of the parameters will be stored + * in it. + * + * @param {module:paramGui~CosmoParams} cosmoParamsInstance + * @param {Object} serializedMessage - message to be sent to the server + */ +function onCosmologicalParamsSet(cosmoParamsInstance, serializedMessage) { + if (!initialSet) { + alert("Initial condition has to be set!"); + return; + } + if (!calculationRunning) { + log("Sending cosmological parameters to server."); + + var alreadySimulated = simulationManager.wasAlreadySimulated(cosmoParamsInstance.parameters); + log("Already simulated? " + alreadySimulated); + if (!alreadySimulated) { + calculationRunning = true; + showActivityIndicator(); + connection.send(JSON.stringify(serializedMessage)); + + $("#simulationProgressModal").modal("show"); + $("#simulationProgressInfo").text("Running calculation... (this may take some time depending on the choice of parameters!)"); + $("#simulationProgressBar").css({width: "0%"}); + $("#simulationProgressBar").text("0%"); + + if (!simulationManager.hasTarget()) { + simulationManager.createSimulation(); + } + /** + * At this point, it is absolutely necessary to create a copy of the + * parameters. If not, any change by the user in the parameters in the + * control panel will be reflected by the parameters stored in the simulation + * object, since both references refer to the same object. + * This results in simulationManager.wasAlreadySimulated always returning + * true and hence preventing any further simulation runs. + */ + var simParams = Object.assign({}, cosmoParamsInstance.parameters); + simulationManager.getTarget().setParameters(simParams); + } else { + $("#alreadySimulatedModal").modal("show"); + } + } +} + +/** + * Loads the given frame. + * + * @param {number} f - frame to load + * @param {bool} replot - if true, fully replot (which includes recalculating + * data limits, axis labels, etc.). otherwise, just swap + * out the data (faster, but this effect decreases with data + * size, since then most of the CPU time will be spent on plotting + * the curve anyways) + */ +function loadFrame(f, replot) { + frame = f; + simulationManager.loadFrame(activeQuantity, f); + + plotTransferFunctionIfVisible(f, replot); + + if (f > 0) + $("#DisplayRedshift").text(round(redshift[f], REDSHIFT_ROUND)); + else if (f == 0) + $("#DisplayRedshift").text(redshift[0]); + + var frameCount = simulationManager.getFrameCount(); + // var percentage = (frameCount > 1) ? frame / (frameCount - 1) : frame / frameCount; + updateTimeline(getLastFrame()); +} + +/** + * Plots the transfer function for the given frame if and only if the plot window + * is visible. + * + * @param {number} f - frame number + * @param {bool} replot - same as in {@link module:RSI~loadFrame} + */ +function plotTransferFunctionIfVisible(f, replot) { + if (plotWindowVisible) { + plotTransferFunction(f, replot); + } +} + +/** + * Finds the minimum and maximum of all transfer functions + * over all frames. + * + * @return {number[]} tuple containing minimum and maximum, in that order + */ +function findTransferFunctionMinMax() { + var min = Infinity, max = -Infinity; + var frameCount = simulationManager.getFrameCount(); + for (var _f = 0; _f < frameCount; ++_f) { + var transferFunctions = simulationManager.getTransferData(activeQuantity, _f); + for (var i = 0; i < transferFunctions.length; ++i) { + var transferFunction = transferFunctions[i]; + var _min = Math.min.apply(null, transferFunction); + var _max = Math.max.apply(null, transferFunction); + + min = Math.min(min, _min); + max = Math.max(max, _max); + } + } + + return [min, max]; +} + +/** + * Plot transfer function in non-single mode, i.e. one quantity but for + * multiple simulations. + * + * @param {number} f - frame number + * @param {bool} replot - same as in {@link module:RSI~loadFrame} + */ +function plotTransferFunctionMulti(f, replot) { + // Transfer function + var tData = simulationManager.getTransferData(activeQuantity, f); + var activeIndices = simulationManager.getActive(); + var datas = []; + for (var i = 0; i < activeIndices.length; ++i) { + var color = colors[activeIndices[i] % colors.length]; + var data = zip(kRange, tData[i]); + datas.push({ + shadowSize: 0, + color: color, + data: data, + }); + } + + transferFunctionPlot = $.plot($("#transferFunctionPlot"), datas, transferPlotOptions); +} + +/** + * Plot transfer function in single mode. + * + * @param {number} f - frame number + */ +function plotTransferFunctionSingle(f) { + var replot = true; + var datas = []; + // Transfer function + for (var i = 0; i < QUANTITIES.length; ++i) { + var tData = simulationManager.getTransferDataOfSingle(QUANTITIES[i], f); + var color = colors[i % colors.length]; + var data = zip(kRange, tData); + datas.push({ + shadowSize: 0, + color: color, + data: data, + }); + } + + transferFunctionPlot = $.plot($("#transferFunctionPlot"), datas, transferPlotOptions); + return; + + if (replot) { + } + else { + transferFunctionPlot.setData(datas); + transferFunctionPlot.draw(); + } +} + +/** + * Plot the transfer function, automatically in the correct mode (single vs. non-single). + * + * @param {number} f - frame number + * @param {bool} replot - same as in {@link module:RSI~loadFrame} + */ +function plotTransferFunction(f, replot) { + if (simulationManager.singleMode) { + plotTransferFunctionSingle(f); + } else { + plotTransferFunctionMulti(f, replot); + } +} + +/******************************************************************************* +* Cl plotting +*******************************************************************************/ + +/** + * Plot Cl spectrum in non-single mode. + */ +function plotClsMulti() { + var plotDatas = []; + + simulationManager.forEachActive(function(index, simulation) { + var dataItem = { + shadowSize: 0, + color: colors[index % colors.length], + data: zip(simulation.Cls.l, simulation.Cls.tCl), + } + plotDatas.push(dataItem); + }); + + $.plot($("#tClPlot"), plotDatas, tClPlotOptions); +} + +/** + * Plot Cl spectrum in single mode. + */ +function plotClsSingle() { + var tuple = simulationManager.getSingleSimulation(); + var singleIndex = tuple[0]; + var singleSimulation = tuple[1]; + + var plotData = { + shadowSize: 0, + color: colors[singleIndex % colors.length], + data: zip(singleSimulation.Cls.l, singleSimulation.Cls.tCl) + }; + $.plot($("#tClPlot"), [plotData], tClPlotOptions); +} + +/******************************************************************************* +* mPk plotting +*******************************************************************************/ + +/** + * Plot matter spectrum in non-single mode. + */ +function plotmPkMulti() { + var plotDatas = []; + + simulationManager.forEachActive(function(index, simulation) { + var dataItem = { + shadowSize: 0, + color: colors[index % colors.length], + data: zip(simulation.mPk.kh, simulation.mPk.Pkh), + } + plotDatas.push(dataItem); + }); + + $.plot($("#mPkPlot"), plotDatas, mPkPlotOptions); +} + +/** + * Plot matter spectrum in single mode. + */ +function plotmPkSingle() { + var tuple = simulationManager.getSingleSimulation(); + var singleIndex = tuple[0]; + var singleSimulation = tuple[1]; + + var plotData = { + shadowSize: 0, + color: colors[singleIndex % colors.length], + data: zip(singleSimulation.mPk.kh, singleSimulation.mPk.Pkh) + }; + $.plot($("#mPkPlot"), [plotData], mPkPlotOptions); +} + +/******************************************************************************* +* Static plotting (i.e. Cl's and mPk) +*******************************************************************************/ + +/** + * Plot the static plots (Cl's and matter spectrum) in the appropriate mode + */ +function plotStatic() { + if (simulationManager.singleMode) { + plotStaticSingle(); + } else { + plotStaticMulti(); + } +} + +/** + * Plot the static plots (Cl's and matter spectrum) only if the plot panel + * is visible. + */ +function plotStaticIfVisible() { + if (plotWindowVisible) + plotStatic(); +} + +/** + * Plot Cl's and matter spectrum in non-single mode. + */ +function plotStaticMulti() { + plotClsMulti(); + plotmPkMulti(); +} + +/** + * Plot Cl's and matter spectrum in single mode. + */ +function plotStaticSingle() { + plotClsSingle(); + plotmPkSingle(); +} + + +/** + * Analogon of the zip function in python. Takes two arrays [a1, a2, a3, ...] and + * [b1, b2, b3, ...] and returns [[a1, b1], [a2, b2], [a3, b3], ...]. + * Required for plotting, as flot.js requires its data to be specified in a 'zipped' + * format. + * + * @param {Object[]} a - first array + * @param {Object[]} b - second array + * + * @return {Array.>}} the zipped array + */ +function zip(a, b) { + var result = []; + var limit = Math.min(a.length, b.length); + for (var i = 0; i < limit; ++i) { + result.push([a[i], b[i]]); + } + return result; +} + +/* + * Player Panel Callbacks + */ + +/** + * Implements {@link PlayerPanel~playPauseCallback}. + */ +function onPlayPause(playing) { + animationRunning = playing; + if (playing) { + if (frame == getLastFrame()) { + frame = 0; + } + } else { + } +} + +/** + * Implements {@link PlayerPanel~scrubCallback}. + */ +function scrubCallback(progress) { + var f = Math.floor((getLastFrame() + 1) * progress); + f = Math.min(getLastFrame(), f); + loadFrame(f); +} + +/** + * Implements {@link PlayerPanel~backFrameCallback}. + */ +function onBackFrame() { + if (frame > 0 && receivedInitial) { + loadFrame(frame - 1); + } +} + +/** + * Implements {@link PlayerPanel~forwardFrameCallback}. + */ +function onForwardFrame() { + if (frame < getLastFrame()) + loadFrame(frame + 1); +} + +/** + * Implements {@link PlayerPanel~toStartCallback}. + */ +function onToStart() { + frame = 0; + loadFrame(frame); +} + +/** + * Implements {@link PlayerPanel~toEndCallback}. + */ +function onToEnd() { + if (receivedInitial) { + loadFrame(getLastFrame()); + } +} + +/** + * Returns the number of the last frame to be displayed. + * If {@link module:RSI~stopAtDecoupling} is true, return the last frame before + * decoupling, otherwise the actual last frame stored. + * + * @return {number} number of last frame + */ +function getLastFrame() { + var frameCount = simulationManager.getFrameCount(); + return lastFrame = (stopAtDecoupling) ? Math.min(decouplingFrame, frameCount - 1) : frameCount - 1; +} + + +/** + * Initializes all components. + */ +function init() { + hideActivityIndicator(); + + window.addEventListener("mousemove", onMouseMove, false); + + parameterGui = new ParameterGui(onInitialConditionSet, onCosmologicalParamsSet); + + simulationManager = new SimulationManager(cmapTexture); + playerPanel = new PlayerPanel( + onPlayPause, + onBackFrame, + onForwardFrame, + onToStart, + onToEnd, + function(e) {}, + scrubCallback + ); + + initQuantityDropdown(); + initColorMapDropdown(); + initGifDialog(); + initImgDialog(); + + initTransferPlot(); + initClPlot(); + initmPkPlot(); + + initPlotCollapseButton(); + + initRedshiftEndToggle(); + + /////////// + // Scene // + /////////// + + container = document.getElementById("container"); + + scene = new THREE.Scene(); + scene.add(simulationManager.getGroup()); + scene.add(simulationManager.getActiveBoxes()); + // scene.add(simulationManager.getCollisionGroup()); + scene.background = new THREE.Color("#4a4a4a"); + + var width = window.innerWidth; + var height = window.innerHeight; + var aspect = width / height; // view aspect ratio + + //////////// + // Camera // + //////////// + + camera = new THREE.PerspectiveCamera(FoV, aspect, 0.1, 10000); + + camera.position.y = 300; + camera.position.z = 500; + camera.position.x = -50; + camera.lookAt(scene.position); + + + ////////////// + // Renderer // + ////////////// + renderer = new THREE.WebGLRenderer({antialias: true}); + renderer.setClearColor(0x53504d); + renderer.setSize(window.innerWidth, window.innerHeight); + renderer.setPixelRatio(window.devicePixelRatio); + renderer.autoClear = false; + + container.innerHTML = ""; + container.appendChild(renderer.domElement); + + ////////////// + // Controls // + ////////////// + controls = new THREE.OrbitControls(camera, renderer.domElement); + + controls.rotateSpeed = 1.0; + controls.zoomSpeed = 3; + controls.panSpeed = 0.8; + + controls.noZoom = false; + controls.noPan = false; + + controls.maxPolarAngle = Math.PI/2; + controls.minDistance = 100; + controls.maxDistance = 10000; + + controls.staticMoving = true; + controls.dynamicDampingFactor = 0.3; + + controls.keys = [65, 83, 68]; + + controls.addEventListener('change', render); + + /****************************************************************** + * SIMULATION TABLE + ******************************************************************/ + + var deleteCallback = function(index) { + simulationManager.delete(index); + simuTable.clear(); + simuTable.populate(simulationManager.getSimulations(), simulationManager.getActive()); + plotStaticIfVisible(); + loadFrame(frame, true); + }; + + var activateCallback = function(index) { + simulationManager.activate(index); + loadFrame(frame, true); + plotStaticIfVisible(); + }; + + var deactivateCallback = function(index) { + simulationManager.deactivate(index); + loadFrame(frame, true); + plotStaticIfVisible(); + }; + + var imageCallback = function(index) { + if (simulationManager.isActive(index)) { + $("#simulationListModal").modal("hide"); + $("#imgExportModal").data("simulationIndex", index).modal("show"); + } + else { + alert("To create an image, the selected simulation needs to be active."); + } + }; + + var gifCallback = function(index) { + if (simulationManager.isActive(index)) { + $("#simulationListModal").modal("hide"); + $("#gifExportModal").data("simulationIndex", index).modal("show"); + } else { + alert("To create a .gif, the selected simulation needs to be active."); + } + // renderGIF(index); + }; + + var singleModeCallback = function(index) { + $("#simulationListModal").modal("hide"); + enterSingleMode(index); + }; + + var focusCameraCallback = function(index) { + if (simulationManager.isActive(index)) { + controls.center.copy(simulationManager.getSimulations()[index].mesh.position); + controls.rotateUp(controls.getPolarAngle()); + controls.rotateLeft(controls.getAzimuthalAngle()); + $("#simulationListModal").modal("hide"); + } else { + alert("To focus the camera on the selected simulation, it needs to be active."); + } + }; + + var loadParamCallback = function(index) { + var parameters = simulationManager.getSimulations()[index].params; + parameterGui.loadCosmoParameters(parameters); + }; + + simuTable = new SimuTable(deleteCallback, activateCallback, deactivateCallback, + gifCallback, imageCallback, singleModeCallback, focusCameraCallback, + loadParamCallback); + + simuTable.createHeader(); + /****************************************************************** + * END OF SIMULATION TABLE + ******************************************************************/ + + // stats = new Stats(); + // stats.domElement.style.position = 'absolute'; + // stats.domElement.style.bottom = '0px'; + // stats.domElement.style.zIndex = 100; + // container.appendChild(stats.domElement); + + window.addEventListener('resize', onWindowResize, false); +} + +/** + * Shows the activity indicator. + */ +function showActivityIndicator() { + $("#activityIndicator").removeClass("activityIndicator-inactive").addClass("activityIndicator-active"); +} + +/** + * Hides the activity indicator. + */ +function hideActivityIndicator() { + $("#activityIndicator").addClass("activityIndicator-inactive").removeClass("activityIndicator-active"); +} + +/** + * Called when the window is resized to update the renderer (which requires + * the window size to render) and the camera (which requires the aspect ratio + * of the window to construct its projection matrix). + */ +function onWindowResize() { + camera.aspect = window.innerWidth / window.innerHeight; + camera.updateProjectionMatrix(); + + renderer.setSize(window.innerWidth, window.innerHeight); + + // Re-read the width of the time line once window refreshes + playerPanel.timeline.refresh(); +} + +/** + * This function is called every time an update (such as an advance in frame, etc.) + * is needed. + * It handles the logic required to play back the animation, such as advancing, + * repeating (if repeat is enabled), pausing and continuing the playback, etc. + * The rate at which this function is called is determined by the FPS. + */ +function step() { + var totalFrames = simulationManager.getFrameCount(); + var lastFrame = getLastFrame(); + if(animationRunning) { + if(frame < lastFrame) { + loadFrame(++frame); + } + else if (frame == lastFrame) { + if (playerPanel.repeat) { + frame = 1; + loadFrame(frame); + } else + playerPanel.pause(); + } + } + setTimeout(step, 1000 / parameterGui.config.animationSpeed); +} + +/** + * Positions the 'scrubber' of the playback timeline at {@link module:RSI~frame} + * given the last frame position. + * + * @param {number} lastFrame - index of last frame + */ +function updateTimeline(lastFrame) { + playerPanel.timeline.scrubTo(frame / lastFrame); +} + + +/** + * Function that is called on every frame of the main loop. + */ +function animate() { + requestAnimationFrame(animate); + controls.update(); + + render(); +} + +/** + * Rendering function, called on every frame of the main loop via + * {@link module:RSI~animate}. + * On each frame, this renders the scene and updates the raycaster. + * Then determines over which plane (if at all) the mouse hovers + * and instructs the {@link SimulationManager} instance to highlight it. + */ +function render() { + raycaster.setFromCamera(mouse, camera); + simulationManager.mousePick(raycaster); + + // renderer.clear(); + renderer.render(scene, camera); + // renderer.clearDepth(); + // stats.update(); +} diff --git a/class/RealSpaceInterface/static/js/gif.js b/class/RealSpaceInterface/static/js/gif.js new file mode 100644 index 00000000..2e4d2042 --- /dev/null +++ b/class/RealSpaceInterface/static/js/gif.js @@ -0,0 +1,3 @@ +// gif.js 0.2.0 - https://github.com/jnordberg/gif.js +(function(f){if(typeof exports==="object"&&typeof module!=="undefined"){module.exports=f()}else if(typeof define==="function"&&define.amd){define([],f)}else{var g;if(typeof window!=="undefined"){g=window}else if(typeof global!=="undefined"){g=global}else if(typeof self!=="undefined"){g=self}else{g=this}g.GIF=f()}})(function(){var define,module,exports;return function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o0&&this._events[type].length>m){this._events[type].warned=true;console.error("(node) warning: possible EventEmitter memory "+"leak detected. %d listeners added. "+"Use emitter.setMaxListeners() to increase limit.",this._events[type].length);if(typeof console.trace==="function"){console.trace()}}}return this};EventEmitter.prototype.on=EventEmitter.prototype.addListener;EventEmitter.prototype.once=function(type,listener){if(!isFunction(listener))throw TypeError("listener must be a function");var fired=false;function g(){this.removeListener(type,g);if(!fired){fired=true;listener.apply(this,arguments)}}g.listener=listener;this.on(type,g);return this};EventEmitter.prototype.removeListener=function(type,listener){var list,position,length,i;if(!isFunction(listener))throw TypeError("listener must be a function");if(!this._events||!this._events[type])return this;list=this._events[type];length=list.length;position=-1;if(list===listener||isFunction(list.listener)&&list.listener===listener){delete this._events[type];if(this._events.removeListener)this.emit("removeListener",type,listener)}else if(isObject(list)){for(i=length;i-- >0;){if(list[i]===listener||list[i].listener&&list[i].listener===listener){position=i;break}}if(position<0)return this;if(list.length===1){list.length=0;delete this._events[type]}else{list.splice(position,1)}if(this._events.removeListener)this.emit("removeListener",type,listener)}return this};EventEmitter.prototype.removeAllListeners=function(type){var key,listeners;if(!this._events)return this;if(!this._events.removeListener){if(arguments.length===0)this._events={};else if(this._events[type])delete this._events[type];return this}if(arguments.length===0){for(key in this._events){if(key==="removeListener")continue;this.removeAllListeners(key)}this.removeAllListeners("removeListener");this._events={};return this}listeners=this._events[type];if(isFunction(listeners)){this.removeListener(type,listeners)}else if(listeners){while(listeners.length)this.removeListener(type,listeners[listeners.length-1])}delete this._events[type];return this};EventEmitter.prototype.listeners=function(type){var ret;if(!this._events||!this._events[type])ret=[];else if(isFunction(this._events[type]))ret=[this._events[type]];else ret=this._events[type].slice();return ret};EventEmitter.prototype.listenerCount=function(type){if(this._events){var evlistener=this._events[type];if(isFunction(evlistener))return 1;else if(evlistener)return evlistener.length}return 0};EventEmitter.listenerCount=function(emitter,type){return emitter.listenerCount(type)};function isFunction(arg){return typeof arg==="function"}function isNumber(arg){return typeof arg==="number"}function isObject(arg){return typeof arg==="object"&&arg!==null}function isUndefined(arg){return arg===void 0}},{}],2:[function(require,module,exports){var UA,browser,mode,platform,ua;ua=navigator.userAgent.toLowerCase();platform=navigator.platform.toLowerCase();UA=ua.match(/(opera|ie|firefox|chrome|version)[\s\/:]([\w\d\.]+)?.*?(safari|version[\s\/:]([\w\d\.]+)|$)/)||[null,"unknown",0];mode=UA[1]==="ie"&&document.documentMode;browser={name:UA[1]==="version"?UA[3]:UA[1],version:mode||parseFloat(UA[1]==="opera"&&UA[4]?UA[4]:UA[2]),platform:{name:ua.match(/ip(?:ad|od|hone)/)?"ios":(ua.match(/(?:webos|android)/)||platform.match(/mac|win|linux/)||["other"])[0]}};browser[browser.name]=true;browser[browser.name+parseInt(browser.version,10)]=true;browser.platform[browser.platform.name]=true;module.exports=browser},{}],3:[function(require,module,exports){var EventEmitter,GIF,browser,extend=function(child,parent){for(var key in parent){if(hasProp.call(parent,key))child[key]=parent[key]}function ctor(){this.constructor=child}ctor.prototype=parent.prototype;child.prototype=new ctor;child.__super__=parent.prototype;return child},hasProp={}.hasOwnProperty,indexOf=[].indexOf||function(item){for(var i=0,l=this.length;iref;i=0<=ref?++j:--j){results.push(null)}return results}.call(this);numWorkers=this.spawnWorkers();if(this.options.globalPalette===true){this.renderNextFrame()}else{for(i=j=0,ref=numWorkers;0<=ref?jref;i=0<=ref?++j:--j){this.renderNextFrame()}}this.emit("start");return this.emit("progress",0)};GIF.prototype.abort=function(){var worker;while(true){worker=this.activeWorkers.shift();if(worker==null){break}this.log("killing active worker");worker.terminate()}this.running=false;return this.emit("abort")};GIF.prototype.spawnWorkers=function(){var j,numWorkers,ref,results;numWorkers=Math.min(this.options.workers,this.frames.length);(function(){results=[];for(var j=ref=this.freeWorkers.length;ref<=numWorkers?jnumWorkers;ref<=numWorkers?j++:j--){results.push(j)}return results}).apply(this).forEach(function(_this){return function(i){var worker;_this.log("spawning worker "+i);worker=new Worker(_this.options.workerScript);worker.onmessage=function(event){_this.activeWorkers.splice(_this.activeWorkers.indexOf(worker),1);_this.freeWorkers.push(worker);return _this.frameFinished(event.data)};return _this.freeWorkers.push(worker)}}(this));return numWorkers};GIF.prototype.frameFinished=function(frame){var i,j,ref;this.log("frame "+frame.index+" finished - "+this.activeWorkers.length+" active");this.finishedFrames++;this.emit("progress",this.finishedFrames/this.frames.length);this.imageParts[frame.index]=frame;if(this.options.globalPalette===true){this.options.globalPalette=frame.globalPalette;this.log("global palette analyzed");if(this.frames.length>2){for(i=j=1,ref=this.freeWorkers.length;1<=ref?jref;i=1<=ref?++j:--j){this.renderNextFrame()}}}if(indexOf.call(this.imageParts,null)>=0){return this.renderNextFrame()}else{return this.finishRendering()}};GIF.prototype.finishRendering=function(){var data,frame,i,image,j,k,l,len,len1,len2,len3,offset,page,ref,ref1,ref2;len=0;ref=this.imageParts;for(j=0,len1=ref.length;j=this.frames.length){return}frame=this.frames[this.nextFrame++];worker=this.freeWorkers.shift();task=this.getTask(frame);this.log("starting frame "+(task.index+1)+" of "+this.frames.length);this.activeWorkers.push(worker);return worker.postMessage(task)};GIF.prototype.getContextData=function(ctx){return ctx.getImageData(0,0,this.options.width,this.options.height).data};GIF.prototype.getImageData=function(image){var ctx;if(this._canvas==null){this._canvas=document.createElement("canvas");this._canvas.width=this.options.width;this._canvas.height=this.options.height}ctx=this._canvas.getContext("2d");ctx.setFill=this.options.background;ctx.fillRect(0,0,this.options.width,this.options.height);ctx.drawImage(image,0,0);return this.getContextData(ctx)};GIF.prototype.getTask=function(frame){var index,task;index=this.frames.indexOf(frame);task={index:index,last:index===this.frames.length-1,delay:frame.delay,transparent:frame.transparent,width:this.options.width,height:this.options.height,quality:this.options.quality,dither:this.options.dither,globalPalette:this.options.globalPalette,repeat:this.options.repeat,canTransfer:browser.name==="chrome"};if(frame.data!=null){task.data=frame.data}else if(frame.context!=null){task.data=this.getContextData(frame.context)}else if(frame.image!=null){task.data=this.getImageData(frame.image)}else{throw new Error("Invalid frame")}return task};GIF.prototype.log=function(){var args;args=1<=arguments.length?slice.call(arguments,0):[];if(!this.options.debug){return}return console.log.apply(console,args)};return GIF}(EventEmitter);module.exports=GIF},{"./browser.coffee":2,events:1}]},{},[3])(3)}); +//# sourceMappingURL=gif.js.map diff --git a/class/RealSpaceInterface/static/js/gif.worker.js b/class/RealSpaceInterface/static/js/gif.worker.js new file mode 100644 index 00000000..269624e6 --- /dev/null +++ b/class/RealSpaceInterface/static/js/gif.worker.js @@ -0,0 +1,3 @@ +// gif.worker.js 0.2.0 - https://github.com/jnordberg/gif.js +(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o=ByteArray.pageSize)this.newPage();this.pages[this.page][this.cursor++]=val};ByteArray.prototype.writeUTFBytes=function(string){for(var l=string.length,i=0;i=0)this.dispose=disposalCode};GIFEncoder.prototype.setRepeat=function(repeat){this.repeat=repeat};GIFEncoder.prototype.setTransparent=function(color){this.transparent=color};GIFEncoder.prototype.addFrame=function(imageData){this.image=imageData;this.colorTab=this.globalPalette&&this.globalPalette.slice?this.globalPalette:null;this.getImagePixels();this.analyzePixels();if(this.globalPalette===true)this.globalPalette=this.colorTab;if(this.firstFrame){this.writeLSD();this.writePalette();if(this.repeat>=0){this.writeNetscapeExt()}}this.writeGraphicCtrlExt();this.writeImageDesc();if(!this.firstFrame&&!this.globalPalette)this.writePalette();this.writePixels();this.firstFrame=false};GIFEncoder.prototype.finish=function(){this.out.writeByte(59)};GIFEncoder.prototype.setQuality=function(quality){if(quality<1)quality=1;this.sample=quality};GIFEncoder.prototype.setDither=function(dither){if(dither===true)dither="FloydSteinberg";this.dither=dither};GIFEncoder.prototype.setGlobalPalette=function(palette){this.globalPalette=palette};GIFEncoder.prototype.getGlobalPalette=function(){return this.globalPalette&&this.globalPalette.slice&&this.globalPalette.slice(0)||this.globalPalette};GIFEncoder.prototype.writeHeader=function(){this.out.writeUTFBytes("GIF89a")};GIFEncoder.prototype.analyzePixels=function(){if(!this.colorTab){this.neuQuant=new NeuQuant(this.pixels,this.sample);this.neuQuant.buildColormap();this.colorTab=this.neuQuant.getColormap()}if(this.dither){this.ditherPixels(this.dither.replace("-serpentine",""),this.dither.match(/-serpentine/)!==null)}else{this.indexPixels()}this.pixels=null;this.colorDepth=8;this.palSize=7;if(this.transparent!==null){this.transIndex=this.findClosest(this.transparent,true)}};GIFEncoder.prototype.indexPixels=function(imgq){var nPix=this.pixels.length/3;this.indexedPixels=new Uint8Array(nPix);var k=0;for(var j=0;j=0&&x1+x=0&&y1+y>16,(c&65280)>>8,c&255,used)};GIFEncoder.prototype.findClosestRGB=function(r,g,b,used){if(this.colorTab===null)return-1;if(this.neuQuant&&!used){return this.neuQuant.lookupRGB(r,g,b)}var c=b|g<<8|r<<16;var minpos=0;var dmin=256*256*256;var len=this.colorTab.length;for(var i=0,index=0;i=0){disp=dispose&7}disp<<=2;this.out.writeByte(0|disp|0|transp);this.writeShort(this.delay);this.out.writeByte(this.transIndex);this.out.writeByte(0)};GIFEncoder.prototype.writeImageDesc=function(){this.out.writeByte(44);this.writeShort(0);this.writeShort(0);this.writeShort(this.width);this.writeShort(this.height);if(this.firstFrame||this.globalPalette){this.out.writeByte(0)}else{this.out.writeByte(128|0|0|0|this.palSize)}};GIFEncoder.prototype.writeLSD=function(){this.writeShort(this.width);this.writeShort(this.height);this.out.writeByte(128|112|0|this.palSize);this.out.writeByte(0);this.out.writeByte(0)};GIFEncoder.prototype.writeNetscapeExt=function(){this.out.writeByte(33);this.out.writeByte(255);this.out.writeByte(11);this.out.writeUTFBytes("NETSCAPE2.0");this.out.writeByte(3);this.out.writeByte(1);this.writeShort(this.repeat);this.out.writeByte(0)};GIFEncoder.prototype.writePalette=function(){this.out.writeBytes(this.colorTab);var n=3*256-this.colorTab.length;for(var i=0;i>8&255)};GIFEncoder.prototype.writePixels=function(){var enc=new LZWEncoder(this.width,this.height,this.indexedPixels,this.colorDepth);enc.encode(this.out)};GIFEncoder.prototype.stream=function(){return this.out};module.exports=GIFEncoder},{"./LZWEncoder.js":2,"./TypedNeuQuant.js":3}],2:[function(require,module,exports){var EOF=-1;var BITS=12;var HSIZE=5003;var masks=[0,1,3,7,15,31,63,127,255,511,1023,2047,4095,8191,16383,32767,65535];function LZWEncoder(width,height,pixels,colorDepth){var initCodeSize=Math.max(2,colorDepth);var accum=new Uint8Array(256);var htab=new Int32Array(HSIZE);var codetab=new Int32Array(HSIZE);var cur_accum,cur_bits=0;var a_count;var free_ent=0;var maxcode;var clear_flg=false;var g_init_bits,ClearCode,EOFCode;function char_out(c,outs){accum[a_count++]=c;if(a_count>=254)flush_char(outs)}function cl_block(outs){cl_hash(HSIZE);free_ent=ClearCode+2;clear_flg=true;output(ClearCode,outs)}function cl_hash(hsize){for(var i=0;i=0){disp=hsize_reg-i;if(i===0)disp=1;do{if((i-=disp)<0)i+=hsize_reg;if(htab[i]===fcode){ent=codetab[i];continue outer_loop}}while(htab[i]>=0)}output(ent,outs);ent=c;if(free_ent<1<0){outs.writeByte(a_count);outs.writeBytes(accum,0,a_count);a_count=0}}function MAXCODE(n_bits){return(1<0)cur_accum|=code<=8){char_out(cur_accum&255,outs);cur_accum>>=8;cur_bits-=8}if(free_ent>maxcode||clear_flg){if(clear_flg){maxcode=MAXCODE(n_bits=g_init_bits);clear_flg=false}else{++n_bits;if(n_bits==BITS)maxcode=1<0){char_out(cur_accum&255,outs);cur_accum>>=8;cur_bits-=8}flush_char(outs)}}this.encode=encode}module.exports=LZWEncoder},{}],3:[function(require,module,exports){var ncycles=100;var netsize=256;var maxnetpos=netsize-1;var netbiasshift=4;var intbiasshift=16;var intbias=1<>betashift;var betagamma=intbias<>3;var radiusbiasshift=6;var radiusbias=1<>3);var i,v;for(i=0;i>=netbiasshift;network[i][1]>>=netbiasshift;network[i][2]>>=netbiasshift;network[i][3]=i}}function altersingle(alpha,i,b,g,r){network[i][0]-=alpha*(network[i][0]-b)/initalpha;network[i][1]-=alpha*(network[i][1]-g)/initalpha;network[i][2]-=alpha*(network[i][2]-r)/initalpha}function alterneigh(radius,i,b,g,r){var lo=Math.abs(i-radius);var hi=Math.min(i+radius,netsize);var j=i+1;var k=i-1;var m=1;var p,a;while(jlo){a=radpower[m++];if(jlo){p=network[k--];p[0]-=a*(p[0]-b)/alpharadbias;p[1]-=a*(p[1]-g)/alpharadbias;p[2]-=a*(p[2]-r)/alpharadbias}}}function contest(b,g,r){var bestd=~(1<<31);var bestbiasd=bestd;var bestpos=-1;var bestbiaspos=bestpos;var i,n,dist,biasdist,betafreq;for(i=0;i>intbiasshift-netbiasshift);if(biasdist>betashift;freq[i]-=betafreq;bias[i]+=betafreq<>1;for(j=previouscol+1;j>1;for(j=previouscol+1;j<256;j++)netindex[j]=maxnetpos}function inxsearch(b,g,r){var a,p,dist;var bestd=1e3;var best=-1;var i=netindex[g];var j=i-1;while(i=0){if(i=bestd)i=netsize;else{i++;if(dist<0)dist=-dist;a=p[0]-b;if(a<0)a=-a;dist+=a;if(dist=0){p=network[j];dist=g-p[1];if(dist>=bestd)j=-1;else{j--;if(dist<0)dist=-dist;a=p[0]-b;if(a<0)a=-a;dist+=a;if(dist>radiusbiasshift;if(rad<=1)rad=0;for(i=0;i=lengthcount)pix-=lengthcount;i++;if(delta===0)delta=1;if(i%delta===0){alpha-=alpha/alphadec;radius-=radius/radiusdec;rad=radius>>radiusbiasshift;if(rad<=1)rad=0;for(j=0;j= this.count) { + throw "GridLayout error: index higher than maximum number of items in layout"; + } + + row = Math.floor(index / this.columns); + column = index % this.columns; + + return [row, column]; +} + +/** + * Get the actual position (in correct units of size) of + * the item defined by index. + */ +GridLayout.prototype.getWorldPosition = function(index) { + var pos = this.getPosition(index); + + var row = pos[0]; + var col = pos[1]; + + var x = 0, y = 0; + var dx = Math.floor(this.columns / 2); + var dy = Math.floor(this.rows / 2); + if (this.columns % 2 == 0) + dx -= 1 / 2; + if (this.rows % 2 == 0) + dy -= 1 / 2; + x = (col - dx) * (this.size + this.margin); + y = (row - dy) * (this.size + this.margin); + + return [x, y]; +} diff --git a/class/RealSpaceInterface/static/js/jquery.flot.axislabels.js b/class/RealSpaceInterface/static/js/jquery.flot.axislabels.js new file mode 100644 index 00000000..c4b3bca9 --- /dev/null +++ b/class/RealSpaceInterface/static/js/jquery.flot.axislabels.js @@ -0,0 +1,466 @@ +/* +Axis Labels Plugin for flot. +http://github.com/markrcote/flot-axislabels + +Original code is Copyright (c) 2010 Xuan Luo. +Original code was released under the GPLv3 license by Xuan Luo, September 2010. +Original code was rereleased under the MIT license by Xuan Luo, April 2012. + +Permission is hereby granted, free of charge, to any person obtaining +a copy of this software and associated documentation files (the +"Software"), to deal in the Software without restriction, including +without limitation the rights to use, copy, modify, merge, publish, +distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to +the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + */ + +(function ($) { + var options = { + axisLabels: { + show: true + } + }; + + function canvasSupported() { + return !!document.createElement('canvas').getContext; + } + + function canvasTextSupported() { + if (!canvasSupported()) { + return false; + } + var dummy_canvas = document.createElement('canvas'); + var context = dummy_canvas.getContext('2d'); + return typeof context.fillText == 'function'; + } + + function css3TransitionSupported() { + var div = document.createElement('div'); + return typeof div.style.MozTransition != 'undefined' // Gecko + || typeof div.style.OTransition != 'undefined' // Opera + || typeof div.style.webkitTransition != 'undefined' // WebKit + || typeof div.style.transition != 'undefined'; + } + + + function AxisLabel(axisName, position, padding, plot, opts) { + this.axisName = axisName; + this.position = position; + this.padding = padding; + this.plot = plot; + this.opts = opts; + this.width = 0; + this.height = 0; + } + + AxisLabel.prototype.cleanup = function() { + }; + + + CanvasAxisLabel.prototype = new AxisLabel(); + CanvasAxisLabel.prototype.constructor = CanvasAxisLabel; + function CanvasAxisLabel(axisName, position, padding, plot, opts) { + AxisLabel.prototype.constructor.call(this, axisName, position, padding, + plot, opts); + } + + CanvasAxisLabel.prototype.calculateSize = function() { + if (!this.opts.axisLabelFontSizePixels) + this.opts.axisLabelFontSizePixels = 14; + if (!this.opts.axisLabelFontFamily) + this.opts.axisLabelFontFamily = 'sans-serif'; + + var textWidth = this.opts.axisLabelFontSizePixels + this.padding; + var textHeight = this.opts.axisLabelFontSizePixels + this.padding; + if (this.position == 'left' || this.position == 'right') { + this.width = this.opts.axisLabelFontSizePixels + this.padding; + this.height = 0; + } else { + this.width = 0; + this.height = this.opts.axisLabelFontSizePixels + this.padding; + } + }; + + CanvasAxisLabel.prototype.draw = function(box) { + if (!this.opts.axisLabelColour) + this.opts.axisLabelColour = 'black'; + var ctx = this.plot.getCanvas().getContext('2d'); + ctx.save(); + ctx.font = this.opts.axisLabelFontSizePixels + 'px ' + + this.opts.axisLabelFontFamily; + ctx.fillStyle = this.opts.axisLabelColour; + var width = ctx.measureText(this.opts.axisLabel).width; + var height = this.opts.axisLabelFontSizePixels; + var x, y, angle = 0; + if (this.position == 'top') { + x = box.left + box.width/2 - width/2; + y = box.top + height*0.72; + } else if (this.position == 'bottom') { + x = box.left + box.width/2 - width/2; + y = box.top + box.height - height*0.72; + } else if (this.position == 'left') { + x = box.left + height*0.72; + y = box.height/2 + box.top + width/2; + angle = -Math.PI/2; + } else if (this.position == 'right') { + x = box.left + box.width - height*0.72; + y = box.height/2 + box.top - width/2; + angle = Math.PI/2; + } + ctx.translate(x, y); + ctx.rotate(angle); + ctx.fillText(this.opts.axisLabel, 0, 0); + ctx.restore(); + }; + + + HtmlAxisLabel.prototype = new AxisLabel(); + HtmlAxisLabel.prototype.constructor = HtmlAxisLabel; + function HtmlAxisLabel(axisName, position, padding, plot, opts) { + AxisLabel.prototype.constructor.call(this, axisName, position, + padding, plot, opts); + this.elem = null; + } + + HtmlAxisLabel.prototype.calculateSize = function() { + var elem = $('
' + + this.opts.axisLabel + '
'); + this.plot.getPlaceholder().append(elem); + // store height and width of label itself, for use in draw() + this.labelWidth = elem.outerWidth(true); + this.labelHeight = elem.outerHeight(true); + elem.remove(); + + this.width = this.height = 0; + if (this.position == 'left' || this.position == 'right') { + this.width = this.labelWidth + this.padding; + } else { + this.height = this.labelHeight + this.padding; + } + }; + + HtmlAxisLabel.prototype.cleanup = function() { + if (this.elem) { + this.elem.remove(); + } + }; + + HtmlAxisLabel.prototype.draw = function(box) { + this.plot.getPlaceholder().find('#' + this.axisName + 'Label').remove(); + this.elem = $('
' + + this.opts.axisLabel + '
'); + this.plot.getPlaceholder().append(this.elem); + if (this.position == 'top') { + this.elem.css('left', box.left + box.width/2 - this.labelWidth/2 + + 'px'); + this.elem.css('top', box.top + 'px'); + } else if (this.position == 'bottom') { + this.elem.css('left', box.left + box.width/2 - this.labelWidth/2 + + 'px'); + this.elem.css('top', box.top + box.height - this.labelHeight + + 'px'); + } else if (this.position == 'left') { + this.elem.css('top', box.top + box.height/2 - this.labelHeight/2 + + 'px'); + this.elem.css('left', box.left + 'px'); + } else if (this.position == 'right') { + this.elem.css('top', box.top + box.height/2 - this.labelHeight/2 + + 'px'); + this.elem.css('left', box.left + box.width - this.labelWidth + + 'px'); + } + }; + + + CssTransformAxisLabel.prototype = new HtmlAxisLabel(); + CssTransformAxisLabel.prototype.constructor = CssTransformAxisLabel; + function CssTransformAxisLabel(axisName, position, padding, plot, opts) { + HtmlAxisLabel.prototype.constructor.call(this, axisName, position, + padding, plot, opts); + } + + CssTransformAxisLabel.prototype.calculateSize = function() { + HtmlAxisLabel.prototype.calculateSize.call(this); + this.width = this.height = 0; + if (this.position == 'left' || this.position == 'right') { + this.width = this.labelHeight + this.padding; + } else { + this.height = this.labelHeight + this.padding; + } + }; + + CssTransformAxisLabel.prototype.transforms = function(degrees, x, y) { + var stransforms = { + '-moz-transform': '', + '-webkit-transform': '', + '-o-transform': '', + '-ms-transform': '' + }; + if (x != 0 || y != 0) { + var stdTranslate = ' translate(' + x + 'px, ' + y + 'px)'; + stransforms['-moz-transform'] += stdTranslate; + stransforms['-webkit-transform'] += stdTranslate; + stransforms['-o-transform'] += stdTranslate; + stransforms['-ms-transform'] += stdTranslate; + } + if (degrees != 0) { + var rotation = degrees / 90; + var stdRotate = ' rotate(' + degrees + 'deg)'; + stransforms['-moz-transform'] += stdRotate; + stransforms['-webkit-transform'] += stdRotate; + stransforms['-o-transform'] += stdRotate; + stransforms['-ms-transform'] += stdRotate; + } + var s = 'top: 0; left: 0; '; + for (var prop in stransforms) { + if (stransforms[prop]) { + s += prop + ':' + stransforms[prop] + ';'; + } + } + s += ';'; + return s; + }; + + CssTransformAxisLabel.prototype.calculateOffsets = function(box) { + var offsets = { x: 0, y: 0, degrees: 0 }; + if (this.position == 'bottom') { + offsets.x = box.left + box.width/2 - this.labelWidth/2; + offsets.y = box.top + box.height - this.labelHeight; + } else if (this.position == 'top') { + offsets.x = box.left + box.width/2 - this.labelWidth/2; + offsets.y = box.top; + } else if (this.position == 'left') { + offsets.degrees = -90; + offsets.x = box.left - this.labelWidth/2 + this.labelHeight/2; + offsets.y = box.height/2 + box.top; + } else if (this.position == 'right') { + offsets.degrees = 90; + offsets.x = box.left + box.width - this.labelWidth/2 + - this.labelHeight/2; + offsets.y = box.height/2 + box.top; + } + offsets.x = Math.round(offsets.x); + offsets.y = Math.round(offsets.y); + + return offsets; + }; + + CssTransformAxisLabel.prototype.draw = function(box) { + this.plot.getPlaceholder().find("." + this.axisName + "Label").remove(); + var offsets = this.calculateOffsets(box); + this.elem = $('
' + this.opts.axisLabel + '
'); + this.plot.getPlaceholder().append(this.elem); + }; + + + IeTransformAxisLabel.prototype = new CssTransformAxisLabel(); + IeTransformAxisLabel.prototype.constructor = IeTransformAxisLabel; + function IeTransformAxisLabel(axisName, position, padding, plot, opts) { + CssTransformAxisLabel.prototype.constructor.call(this, axisName, + position, padding, + plot, opts); + this.requiresResize = false; + } + + IeTransformAxisLabel.prototype.transforms = function(degrees, x, y) { + // I didn't feel like learning the crazy Matrix stuff, so this uses + // a combination of the rotation transform and CSS positioning. + var s = ''; + if (degrees != 0) { + var rotation = degrees/90; + while (rotation < 0) { + rotation += 4; + } + s += ' filter: progid:DXImageTransform.Microsoft.BasicImage(rotation=' + rotation + '); '; + // see below + this.requiresResize = (this.position == 'right'); + } + if (x != 0) { + s += 'left: ' + x + 'px; '; + } + if (y != 0) { + s += 'top: ' + y + 'px; '; + } + return s; + }; + + IeTransformAxisLabel.prototype.calculateOffsets = function(box) { + var offsets = CssTransformAxisLabel.prototype.calculateOffsets.call( + this, box); + // adjust some values to take into account differences between + // CSS and IE rotations. + if (this.position == 'top') { + // FIXME: not sure why, but placing this exactly at the top causes + // the top axis label to flip to the bottom... + offsets.y = box.top + 1; + } else if (this.position == 'left') { + offsets.x = box.left; + offsets.y = box.height/2 + box.top - this.labelWidth/2; + } else if (this.position == 'right') { + offsets.x = box.left + box.width - this.labelHeight; + offsets.y = box.height/2 + box.top - this.labelWidth/2; + } + return offsets; + }; + + IeTransformAxisLabel.prototype.draw = function(box) { + CssTransformAxisLabel.prototype.draw.call(this, box); + if (this.requiresResize) { + this.elem = this.plot.getPlaceholder().find("." + this.axisName + + "Label"); + // Since we used CSS positioning instead of transforms for + // translating the element, and since the positioning is done + // before any rotations, we have to reset the width and height + // in case the browser wrapped the text (specifically for the + // y2axis). + this.elem.css('width', this.labelWidth); + this.elem.css('height', this.labelHeight); + } + }; + + + function init(plot) { + plot.hooks.processOptions.push(function (plot, options) { + + if (!options.axisLabels.show) + return; + + // This is kind of a hack. There are no hooks in Flot between + // the creation and measuring of the ticks (setTicks, measureTickLabels + // in setupGrid() ) and the drawing of the ticks and plot box + // (insertAxisLabels in setupGrid() ). + // + // Therefore, we use a trick where we run the draw routine twice: + // the first time to get the tick measurements, so that we can change + // them, and then have it draw it again. + var secondPass = false; + + var axisLabels = {}; + var axisOffsetCounts = { left: 0, right: 0, top: 0, bottom: 0 }; + + var defaultPadding = 2; // padding between axis and tick labels + plot.hooks.draw.push(function (plot, ctx) { + var hasAxisLabels = false; + if (!secondPass) { + // MEASURE AND SET OPTIONS + $.each(plot.getAxes(), function(axisName, axis) { + var opts = axis.options // Flot 0.7 + || plot.getOptions()[axisName]; // Flot 0.6 + + // Handle redraws initiated outside of this plug-in. + if (axisName in axisLabels) { + axis.labelHeight = axis.labelHeight - + axisLabels[axisName].height; + axis.labelWidth = axis.labelWidth - + axisLabels[axisName].width; + opts.labelHeight = axis.labelHeight; + opts.labelWidth = axis.labelWidth; + axisLabels[axisName].cleanup(); + delete axisLabels[axisName]; + } + + if (!opts || !opts.axisLabel || !axis.show) + return; + + hasAxisLabels = true; + var renderer = null; + + if (!opts.axisLabelUseHtml && + navigator.appName == 'Microsoft Internet Explorer') { + var ua = navigator.userAgent; + var re = new RegExp("MSIE ([0-9]{1,}[\.0-9]{0,})"); + if (re.exec(ua) != null) { + rv = parseFloat(RegExp.$1); + } + if (rv >= 9 && !opts.axisLabelUseCanvas && !opts.axisLabelUseHtml) { + renderer = CssTransformAxisLabel; + } else if (!opts.axisLabelUseCanvas && !opts.axisLabelUseHtml) { + renderer = IeTransformAxisLabel; + } else if (opts.axisLabelUseCanvas) { + renderer = CanvasAxisLabel; + } else { + renderer = HtmlAxisLabel; + } + } else { + if (opts.axisLabelUseHtml || (!css3TransitionSupported() && !canvasTextSupported()) && !opts.axisLabelUseCanvas) { + renderer = HtmlAxisLabel; + } else if (opts.axisLabelUseCanvas || !css3TransitionSupported()) { + renderer = CanvasAxisLabel; + } else { + renderer = CssTransformAxisLabel; + } + } + + var padding = opts.axisLabelPadding === undefined ? + defaultPadding : opts.axisLabelPadding; + + axisLabels[axisName] = new renderer(axisName, + axis.position, padding, + plot, opts); + + // flot interprets axis.labelHeight and .labelWidth as + // the height and width of the tick labels. We increase + // these values to make room for the axis label and + // padding. + + axisLabels[axisName].calculateSize(); + + // AxisLabel.height and .width are the size of the + // axis label and padding. + // Just set opts here because axis will be sorted out on + // the redraw. + + opts.labelHeight = axis.labelHeight + + axisLabels[axisName].height; + opts.labelWidth = axis.labelWidth + + axisLabels[axisName].width; + }); + + // If there are axis labels, re-draw with new label widths and + // heights. + + if (hasAxisLabels) { + secondPass = true; + plot.setupGrid(); + plot.draw(); + } + } else { + secondPass = false; + // DRAW + $.each(plot.getAxes(), function(axisName, axis) { + var opts = axis.options // Flot 0.7 + || plot.getOptions()[axisName]; // Flot 0.6 + if (!opts || !opts.axisLabel || !axis.show) + return; + + axisLabels[axisName].draw(axis.box); + }); + } + }); + }); + } + + + $.plot.plugins.push({ + init: init, + options: options, + name: 'axisLabels', + version: '2.0' + }); +})(jQuery); diff --git a/class/RealSpaceInterface/static/js/paramGui.js b/class/RealSpaceInterface/static/js/paramGui.js new file mode 100644 index 00000000..c54e0164 --- /dev/null +++ b/class/RealSpaceInterface/static/js/paramGui.js @@ -0,0 +1,397 @@ +/** @module paramGui */ + +/** + * Initial Condition Type. Either Gaussian (0) or Scale Invariant (1). + * + * @typedef {number} IC_TYPE + */ +const IC_TYPE = { + GAUSSIAN: 0, + SCALE_INVARIANT: 1, +}; + +/** + * Set of initial parameters providing the data structure for the ParameterGui. + * Reads default parameters from {@link DEFAULT_INITIAL} and default redshifts + * from {@link DEFAULT_REDSHIFTS}. + * + * @typedef {Object} ParamSet + * @constructor + * + * @property {number} scale - side length of 2D cross section of universe in Mpc + * @property {module:paramGui~IC_TYPE} initialType - either + * {@link IC_TYPE.GAUSSIAN} or + * {@link IC_TYPE.SCALE_INVARIANT} + * @property {bool} limitModes - true if modes are to be limited, false otherwise + * @property {number} minMode - minimum mode wave number in 1 / Mpc + * @property {number} minMode - maximum mode wave number in 1 / Mpc + * @property {number} ns - primordial tilt n_s + * @property {number} resolution - the side length of the mesh in number of vertices + * + * @param {module:RSI~initialConditionSetCallback} setInitialConditions - callback + */ +function ParamSet(setInitialConditions) { + this.scale = DEFAULT_INITIAL.scale; + this.initialType = IC_TYPE.GAUSSIAN; + this.sigmaGauss = DEFAULT_INITIAL.sigmaGauss; + this.limitModes = false; + this.minMode = 1; + this.maxMode = 10; + this.ns = DEFAULT_INITIAL.n_s; + this.resolution = DEFAULT_INITIAL.resolution; + + var self = this; + + var initialCallback = function() { + setInitialConditions(self); + }; + + this.setInitialSI = initialCallback; + this.setInitialGauss = initialCallback; + + this.redshift = Object.assign([], DEFAULT_REDSHIFTS); + this.modal = new RedshiftModal( + this.redshift, + function(redshift) { + self.redshift = redshift; + } + ); + + this.configureRedshift = function() { + self.modal.show(); + }; +}; + +/** + * Returns an object according to the communication protocol + * to be sent as JSON object to the server specifying the initial + * conditions. + * + * @return {Object} the object to be sent to the server + */ +ParamSet.prototype.serializeInitial = function() { + var dataType = (this.initialType === IC_TYPE.GAUSSIAN) ? "Gaussian" : "SI"; + var SILimit; + if (this.initialType === IC_TYPE.GAUSSIAN || !this.limitModes) + SILimit = "None"; + else + SILimit = [this.minMode, this.maxMode]; + + var result = { + type: "Initial", + params: { + xScale: Math.floor(this.scale), + resolution: this.resolution, + initialDataType: dataType, + sigma: this.sigmaGauss, + SILimit: SILimit, + n_s: this.ns, + redshift: this.redshift, + } + }; + + return result; +}; + +/***************************************************************************************/ + +/** + * Represents the set of cosmological parameters (that are + * not initial state parameters). Reads the set of parameters + * exposed to the user from {@link COSMOLOGICAL_PARAMETER_LIST}. + * + * @typedef {Object} CosmoParams + * @constructor + * @param {module:RSI~cosmologicalParametersSetCallback} + */ +function CosmoParams(cosmoCallback) { + this.config = COSMOLOGICAL_PARAMETER_LIST; + this.additionalParameters = ADDITIONAL_CLASS_PARAMETERS; + + this.parameters = this.buildParameterObject(); + this.cosmoCallback = cosmoCallback; +} + +/** + * Builds the object which is passed to dat.gui. + */ +CosmoParams.prototype.buildParameterObject = function() { + var result = {}; + for (var entry of this.config) { + result[entry.name] = entry.default; + } + return result; +}; + +/** + * Resets all parameters to their default value. + */ +CosmoParams.prototype.resetParameters = function() { + for (var entry of this.config) { + this.parameters[entry.name] = entry.default; + } +}; + +/** + * This is called once the user presses the button to set the cosmological parameters + * (which coincides with the button to start the calculation). + * This will call the {@link module:RSI~cosmologicalParametersSetCallback} instance + * passed in the {@link CosmoParams} constructor. + */ +CosmoParams.prototype.setCosmological = function() { + var result = { + type: "Cosmo", + params: this.serialize(), + }; + this.cosmoCallback(this, result); +}; + +/** + * Converts the user specified cosmological parameters into a representation + * that can be sent to the server. + * + * @return {Object} object to be sent to the server + */ +CosmoParams.prototype.serialize = function() { + var serialized = {}; + for (var entry of this.config) { + if (entry.hasOwnProperty("replaceBy")) { + var replacement = entry.replaceBy(this.parameters); + for (var key in replacement) { + serialized[key] = replacement[key]; + } + } + else { + serialized[entry.name] = this.parameters[entry.name]; + } + } + for (var key in this.additionalParameters) { + serialized[key] = this.additionalParameters[key]; + } + + return serialized; +}; + +CosmoParams.prototype.loadParameters = function(parameters) { + var self = this; + Object.keys(parameters).forEach(function(key) { + self.parameters[key] = parameters[key]; + }); +}; + + +/** + * This class provides the graphical user interface that controls the inital + * + cosmological parameters of the simulation as well as other properties, + * such as the animation rate, whether or not grids are shown, etc. + * + * @typedef {Object} ParameterGui + * @constructor + * @param {module:RSI~initialConditionSetCallback} setInitialConditions + * @param {module:RSI~cosmologicalParametersSetCallback} setCosmologicalParams + */ +function ParameterGui(setInitialConditions, setCosmologicalParams) { + this.gui = new dat.GUI({ width: 300 }); + this.gui.domElement.id = "datgui"; + this.paramSet = new ParamSet(setInitialConditions); + this.cosmoParams = new CosmoParams(setCosmologicalParams); + + this.config = { + notFlat: true, + amplitude: 25.0, + resetCamera: function() {controls.reset()}, + orthographicMode: false, + showAxes: true, + dashedAxes: true, + showGrid: true, + animationSpeed: 25, + backgroundColor: "#4a4a4a" + }; + + + this.buildFolders(); +} + +/** + * Create folders for initial condition and cosmological parameters + * and populate them. + * Called via the constructor of {@link ParameterGui}. + */ +ParameterGui.prototype.buildFolders = function() { + this.initialFolder = this.gui.addFolder("Initial Condition"); + this.cosmoFolder = this.gui.addFolder("Cosm. Parameters"); + + this.buildInitialFolder(); + this.buildCosmoFolder(); + this.buildDisplayFolder(); + this.buildControlFolder(); + + this.initialFolder.open(); + this.siFolder.open(); + this.switchToScaleInvariant(); + this.cosmoFolder.open(); +}; + +/** + * Build folder containing initial condition parameters. + */ +ParameterGui.prototype.buildInitialFolder = function() { + this.initialFolder.add(this.paramSet, "scale") + .min(100).max(1600).name("Scale [Mpc]"); + this.initialFolder.add(this.paramSet, "resolution") + .min(64).max(1024).step(1).name("Resolution"); + this.initialFolder.add(this.paramSet, "configureRedshift") + .name("Configure Redshifts"); + + var self = this; + this.gaussianFolder = this.initialFolder.addFolder("Gaussian Initial Conditions"); + this.sigmaGaussCtl = this.gaussianFolder + .add(this.paramSet, "sigmaGauss").min(1).max(30).name("σ [Mpc]"); + this.gaussianFolder + .add(this.paramSet, "setInitialGauss").name("Set Initial Condition"); + this.gaussianFolder.domElement.onclick = function() { + self.switchToGaussian(); + }; + + var siButtonString = "Set Initial Condition"; + + // Create SI folder + this.siFolder = this.initialFolder.addFolder("Scale Invariant Initial Conditions"); + // Add fields + this.siFolder + .add(this.paramSet, "ns").name("ns"); + this.limitModesCtl = this.siFolder + .add(this.paramSet, "limitModes").name("Limit Modes"); + this.limitModesCtl.onChange(function (limitModes) { + if (limitModes) { + self.siFolder.remove(self.set_initial_si); + self.minModeCtl = self.siFolder + .add(self.paramSet, "minMode").name("Min. Mode [1/Mpc]"); + self.maxModeCtl = self.siFolder + .add(self.paramSet, "maxMode").name("Max. Mode [1/Mpc]"); + self.set_initial_si = self.siFolder + .add(self.paramSet, "setInitialSI") + .name(siButtonString); + } else { + self.siFolder.remove(self.minModeCtl); + self.siFolder.remove(self.maxModeCtl); + } + }); + this.set_initial_si = this.siFolder + .add(this.paramSet, "setInitialSI").name(siButtonString); + this.siFolder.domElement.onclick = function() { + self.switchToScaleInvariant(); + }; +}; + +/** + * Build folder containing cosmological parameters. + */ +ParameterGui.prototype.buildCosmoFolder = function() { + for (var param of this.cosmoParams.config) { + var step = param.hasOwnProperty("step") ? param.step : 0.001; + this.cosmoFolder + .add(this.cosmoParams.parameters, param.name) + .step(step) + .min(param.min) + .max(param.max) + .name(param.displayName); + } + + // Rather ugly solution but necessary since calling `listen()` on the + // config attributes above to auto-update them on value change + // prevents user from manually entering a value into the text boxes. + // NOTE: This relies on the internal implementation of dat.gui and is + // therefore not guaranteed to be compatible with future versions of dat.gui. + var self = this; + this.resetConfig = { + resetCosmological: function() { + self.cosmoParams.resetParameters(); + self.refreshCosmoFolder(); + } + }; + + this.cosmoFolder.add(this.resetConfig, "resetCosmological").name("Reset Parameters"); + this.cosmoFolder.add(this.cosmoParams, "setCosmological").name("Start Calculation"); +}; + +ParameterGui.prototype.refreshCosmoFolder = function() { + this.gui.__folders["Cosm. Parameters"].__controllers.forEach(function(ctrl) { + ctrl.updateDisplay(); + }); +}; + +ParameterGui.prototype.loadCosmoParameters = function(parameters) { + this.cosmoParams.loadParameters(parameters); + this.refreshCosmoFolder(); +}; + +ParameterGui.prototype.buildDisplayFolder = function() { + displaySettings = this.gui.addFolder("Display Settings"); + + var self = this; + displaySettings + .add(this.config, 'notFlat') + .name("Show in 3D") + .onChange(function() { + simulationManager.setUniform("notFlat", self.config.notFlat); + }); + + displaySettings + .add(this.config, "showGrid") + .name("Show Grid") + .onChange(function() { + simulationManager.updateGrids(); + }); + + displaySettings + .add(this.config , 'amplitude', 0, 50) + .name("Amplitude") + .onChange(function() { + simulationManager.setUniform("amplitude", self.config.amplitude); + }); + +}; + +/** + * Build the control folder, containing properties like the animation rate, + * background color etc. + */ +ParameterGui.prototype.buildControlFolder = function() { + var self = this; + + this.gui.add(this.config, "animationSpeed", 1, 60).name("FPS").listen().onChange(function() { + fps = self.config.animationSpeed; + }); + + // this.gui.add(this.config, "orthographicMode") + // .name("Orthographic Camera") + // .onChange(toggleCameraMode); + + this.gui.add(this.config, "resetCamera"). name("Reset Camera"); + + this.gui.addColor(this.config, "backgroundColor").name("Background Color") + .onChange(function (value) { + scene.background = new THREE.Color(value); + }); +}; + +/** + * Switch to the menu for Gaussian initial conditions + */ +ParameterGui.prototype.switchToGaussian = function() { + if (this.paramSet.initialType === IC_TYPE.SCALE_INVARIANT) { + this.siFolder.close(); + this.paramSet.initialType = IC_TYPE.GAUSSIAN; + } +}; + +/** + * Switch to the menu for scale invariant initial conditions + */ +ParameterGui.prototype.switchToScaleInvariant = function() { + if (this.paramSet.initialType === IC_TYPE.GAUSSIAN) { + this.gaussianFolder.close(); + this.paramSet.initialType = IC_TYPE.SCALE_INVARIANT; + } +}; diff --git a/class/RealSpaceInterface/static/js/parameterConfig.js b/class/RealSpaceInterface/static/js/parameterConfig.js new file mode 100644 index 00000000..cae53856 --- /dev/null +++ b/class/RealSpaceInterface/static/js/parameterConfig.js @@ -0,0 +1,153 @@ +/* +The parameters the application exposes to the user are configured using this list. +Each parameter is represented by an entry in that list. +An entry is an object containing some required and some optional fields. + +The required fields are: +------------------------ +- `name`: The `name` property is the one that will be used to pass the + parameter value to CLASS. + +- `displayName`: The `displayName` property will be displayed as the label + of the property in both the control panel (on the left of the + application) and in the simulation list. + HTML is allowed. Subscripts use the tag. + +- `min`: Minimum parameter value. + +- `max`: Maximum parameter value. + +- `default`: Default parameter value. + +The optional fields are: +------------------------ +- `step`: The increment by which the parameter will be increased using + the sliders in the control panel. Defaults to 0.001. + +- `replaceBy`: It might be necessary to pass parameters to CLASS + which are functions of other parameters, e.g. the user might + set a value of `omega_m` but CLASS requires `omega_cdm` to be + passed. In this case, a function accepting a dictionary of + all the parameters and returning a dictionary containining + the key-value pairs that are supposed to be passed to CLASS + (see example for `omega_m` below). +*/ + +/** @global */ +var COSMOLOGICAL_PARAMETER_LIST = [ + { + name: "h", + displayName: "h", + min: 0.0, + max: 2.0, + default: 0.67556, + }, + { + name: "omega_b", + displayName: "ωb", + min: 0.0, + max: 1.0, + default: 0.022, + }, + { + name: "omega_m", + displayName: "ωm", + min: 0.0, + max: 1.0, + default: 0.142, + replaceBy: function(parameters) { + return { + "omega_cdm": parameters.omega_m - parameters.omega_b + }; + }, + }, + { + name: "Omega_k", + displayName: "Ωk", + min: -0.2, + max: 0.2, + default: 0.0, + }, + { + name: "N_ur", + displayName: "Neff", + min: 0.0, + max: 30.0, + default: 3.046 + }, + { + name: "w0_fld", + displayName: "w0,fld", + min: -2.0, + max: 0.0, + default: -1.0, + }, + { + name: "wa_fld", + displayName: "wa,fld", + min: -1.0, + max: 1.0, + default: 0.0 + }, +]; + + +/** + * It is possible to pass additional parameters to CLASS using + * the following object. + * + * @global + */ +var ADDITIONAL_CLASS_PARAMETERS = { + "Omega_Lambda": 0, + "YHe": 0.25, +}; + + +/** + * Default redshifts. + * Depending on the value of log, the individual arrays will be created either + * as + *
+ * numpy.logspace(from, to, points) (for log = true)
+ *  or
+ * numpy.linspace(from, to, points) (for  log = false).
+ * 
+ * + * The resulting individual arrays will be concatenated and duplicates removed. + * + * @global + */ +var DEFAULT_REDSHIFTS = [ + { + from: 1000000, + to: 10000, + log: true, + points: 60, + }, + { + from: 10000, + to: 1089, + log: true, + points: 80, + }, + { + from: 1089, + to: 0.01, + log: false, + points: 40, + }, +]; + +/** + * Default Initial Condition Values. + * + * @global + */ +var DEFAULT_INITIAL = { + scale: 400, + resolution: 200, + sigmaGauss: 10.0, + n_s: 0.96 +}; + diff --git a/class/RealSpaceInterface/static/js/playerPanel.js b/class/RealSpaceInterface/static/js/playerPanel.js new file mode 100644 index 00000000..5937e3d6 --- /dev/null +++ b/class/RealSpaceInterface/static/js/playerPanel.js @@ -0,0 +1,190 @@ +/** + * This function will be called when the user presses the play/pause button. + * @callback PlayerPanel~playPauseCallback + * @param {bool} playing - true if movie should be played, false if movie should be paused. + */ + +/** + * This function will be called when the user presses the "back one frame" button. + * @callback PlayerPanel~backFrameCallback + */ + +/** + * This function will be called when the user presses the "forward one frame" button. + * @callback PlayerPanel~forwardFrameCallback + */ + +/** + * This function will be called when the user presses the "Go to Start" button. + * @callback PlayerPanel~toStartCallback + */ + +/** + * This function will be called when the user presses the "Go to End" button. + * @callback PlayerPanel~toEndCallback + */ + +/** + * This function will be called when the user presses the play/pause button. + * @callback PlayerPanel~repeatCallback + * @param {bool} repeating - true if movie should be played in repeat, else false. + */ + +/** + * This function will be called when the user uses the 'scrubber' to move to a specific frame. + * @callback PlayerPanel~scrubCallback + * @param {number} progress - number between 0.0 and 1.0 (inclusive). + */ + +/** + * Represents the player panel. + * @constructor + * @param {PlayerPanel~playPauseCallback} + * @param {PlayerPanel~backFrameCallback} + * @param {PlayerPanel~forwardFrameCallback} + * @param {PlayerPanel~toStartCallback} + * @param {PlayerPanel~toEndCallback} + * @param {PlayerPanel~repeatCallback} + * @param {PlayerPanel~scrubCallback} + */ +function PlayerPanel(playPauseCallback, backFrameCallback, forwardFrameCallback, toStartCallback, toEndCallback, repeatCallback, + scrubCallback) { + this.playPauseCallback = playPauseCallback; + this.backFrameCallback = backFrameCallback; + this.forwardFrameCallback = forwardFrameCallback; + this.toStartCallback = toStartCallback; + this.toEndCallback = toEndCallback; + this.repeatCallback = repeatCallback; + + this.playPauseButton = document.getElementById("playerPlayPauseBtn"); + this.backFrameButton = document.getElementById("playerBackFrameBtn"); + this.forwardFrameButton = document.getElementById("playerForwardFrameBtn"); + this.toStartButton = document.getElementById("playerToStartBtn"); + this.toEndButton = document.getElementById("playerToEndBtn"); + this.repeatButton = document.getElementById("playerRepeatBtn"); + + this.timeline = new Timeline("timeline", "scrubber", scrubCallback); + this.timeline.scrubTo(0); + + this.playing = false; + this.repeat = false; + + this.connectCallbacks(); +} + +PlayerPanel.prototype.connectCallbacks = function() { + var self = this; + this.playPauseButton.onclick = function() { + // Additionally, toggle button + var buttonSpan = self.playPauseButton.firstElementChild; + if (self.playing) { + buttonSpan.classList.remove("oi-media-pause"); + buttonSpan.classList.add("oi-media-play"); + } else { + buttonSpan.classList.remove("oi-media-play"); + buttonSpan.classList.add("oi-media-pause"); + } + self.playing = !self.playing; + self.playPauseCallback(self.playing); + }; + this.backFrameButton.onclick = this.backFrameCallback; + this.forwardFrameButton.onclick = this.forwardFrameCallback; + this.toStartButton.onclick = this.toStartCallback; + this.toEndButton.onclick = this.toEndCallback; + + this.repeatButton.onclick = function() { + if (self.repeat) { + self.repeatButton.classList.remove("btn-success"); + self.repeatButton.classList.add("btn-outline-success"); + } else { + self.repeatButton.classList.remove("btn-outline-success"); + self.repeatButton.classList.add("btn-success"); + } + self.repeat = !self.repeat; + if (self.repeatCallback) { + self.repeatCallback(self.repeat); + } + }; +}; + +PlayerPanel.prototype.pause = function() { + if (this.playing) { + this.playPauseButton.onclick(); + } +}; + +PlayerPanel.prototype.play = function() { + if (!this.playing) { + this.playPauseButton.onclick(); + } +}; + + + + +/* TIMELINE */ +function Timeline(timelineId, scrubberId, scrubCallback) { + this.timeline = document.getElementById(timelineId); + this.scrubber = document.getElementById(scrubberId); + + this.scrubCallback = scrubCallback; + + this.timelineWidth = this.timeline.offsetWidth; + this.scrubberRadius = this.scrubber.offsetWidth / 2; + + + // Center + var dy = this.scrubber.offsetHeight / 2 - this.timeline.offsetHeight / 2; + this.scrubber.style.marginTop = "-" + Math.floor(dy) + "px"; + + // Event handling + this.mouseDown = false; + var self = this; + this.scrubber.addEventListener("mousedown", function(e) { + self.mouseDown = true; + e.stopPropagation(); + }); + + this.timeline.addEventListener("mousedown", function(e) { + self.handleClick(e); + }); + + document.addEventListener("mouseup", function() { + self.mouseDown = false; + }); + + document.addEventListener("mousemove", function(e) { + if (self.mouseDown) { + self.handleClick(e); + } + }); +} + +Timeline.prototype.refresh = function() { + this.timelineWidth = this.timeline.offsetWidth; +}; + +Timeline.prototype.handleClick = function(e) { + var leftBoundary = this.timeline.getBoundingClientRect().left; + var rightBoundary = leftBoundary + this.timelineWidth; + if (e.clientX >= leftBoundary && e.clientX <= rightBoundary) { + var percentage = (e.clientX - leftBoundary) / this.timelineWidth; + this.scrubTo(percentage); + this.scrubCallback(percentage); + } +}; + +Timeline.prototype.scrubTo = function(percentage) { + var pos = percentage * this.timelineWidth - this.scrubberRadius; + this.scrubber.style.marginLeft = pos + "px"; + + this.timeline.style.background = this.generateGradientCSS(percentage); +}; + +Timeline.prototype.generateGradientCSS = function(percent) { + percent *= 100; + // var result = "linear-gradient(to right, rgba(255, 0, 0, 0.75) 0%, rgba(255, 0, 0, 0.75) " + percent + "%, #222 " + percent + "%)"; + var result = "linear-gradient(to right, transparent 0%, transparent " + percent + "%, #222 " + percent + "%)"; + result = result + ", repeating-linear-gradient(45deg, hsl(134, 61%, 35%) 0%, hsl(134, 61%, 35%) 2%, hsl(134, 61%, 41%) 2%, hsl(134, 61%, 41%) 4%)"; + return result; +}; diff --git a/class/RealSpaceInterface/static/js/redshiftModal.js b/class/RealSpaceInterface/static/js/redshiftModal.js new file mode 100644 index 00000000..2ea6c994 --- /dev/null +++ b/class/RealSpaceInterface/static/js/redshiftModal.js @@ -0,0 +1,253 @@ +/** + * @callback RedshiftModal~saveCallback + * @param {Object} config - redshift configuration; + * for documentation on format, see {@link DEFAULT_REDSHIFTS} + */ + +/** + * Redshift Modal that allows user control over redshift sampling. + * @typedef {Object} RedshiftModal + * + * @constructor + * @param {Object} initial state, probably {@link DEFAULT_REDSHIFTS} + * @param {RedshiftModal~saveCallback} callback - callback to be called once user saves + */ +function RedshiftModal(initial, callback) { + this.modal = $("#redshift-modal"); + this.grid = $("#redshift-modal-grid"); + this.initial = initial; + + this.init(initial); + this.callback = callback; +} + +/** + * Initialize the modal with the initial configuration passed to the {@link RedshiftModal} constructor. + * + * @param {Object} initial - initial configuration + */ +RedshiftModal.prototype.init = function(initial) { + this.load(initial); + + // Deactivate first delete button + this.grid.find(".redshift-modal-btn-delete").first().prop("disabled", true); + + var self = this; + this.modal.find("#redshift-modal-save").click(function(e) { + self.clearAlerts(); + if (self.validate()) { + self.callback(self.serialize()); + self.hide(); + } + }); + + this.modal.find("#redshift-modal-cancel").click(function(e) { + self.clear(); + self.load(self.initial); + }); +}; + +/** + * Removes all entries + */ +RedshiftModal.prototype.clear = function() { + this.grid.children().remove(); +}; + +/** + * Show the modal + */ +RedshiftModal.prototype.show = function() { + this.modal.modal("show"); +}; + +/** + * Hide the modal + */ +RedshiftModal.prototype.hide = function() { + this.modal.modal("hide"); +}; + +/** + * Create an empty row template + * @return {Object} row + */ +RedshiftModal.prototype.createRow = function() { + return $("
").addClass("alert").addClass("alert-warning").text(message); + this.modal.find(".modal-body").append(element); +}; + +/** + * Clear all alerts. + */ +RedshiftModal.prototype.clearAlerts = function() { + this.modal.find(".alert").remove(); +}; + +/** + * Validate input fields and display warnings if input fields + * contain illegal values. + * + * @return {bool} true if all inputs are valid; false otherwise. + */ +RedshiftModal.prototype.validate = function() { + var self = this; + var return_ = false; + + var values = this.modal.find(".redshift-modal-z").map(function() { + if (isNaN(this.value)) { + self.alert("Invalid value encountered: " + this.value); + return_ = true; + } + var value = parseFloat(this.value); + return value; + }).get(); + + var points = this.modal.find(".redshift-modal-samples").map(function() { + if (isNaN(this.value)) { + self.alert("Invalid point count encountered: " + this.value); + return_ = true; + } + var value = parseInt(this.value); + if (value <= 0) { + self.alert("Invalid point count encountered: " + value); + return_ = true; + } + return value; + }).get(); + + if (return_) { + return false; + } + + for (var i = 0; i < values.length - 1; ++i) { + if (values[i] <= values[i + 1]) { + self.alert("Redshifts must be decreasing!"); + return false; + } + } + + return true; +}; + +/** + * Constructs an object representing the user's choice of z values. + * For an example of the format, see {@link DEFAULT_REDSHIFTS}. + */ +RedshiftModal.prototype.serialize = function() { + var z = this.modal.find(".redshift-modal-z").map(function() { + return parseFloat(this.value); + }); + + var points = this.modal.find(".redshift-modal-samples").map(function() { + return parseInt(this.value); + }); + + var logarithmic = this.modal.find(".redshift-modal-spacing").map(function() { + return this.value == 0; + }); + + var result = []; + for (var i = 0; i < z.length - 1; ++i) { + result.push({ + from: z[i], + to: z[i + 1], + points: points[i], + log: logarithmic[i], + }); + } + return result; +}; + +/** + * The 'inverse' operation of {@link RedshiftModal#serialize}. + * Takes an object of the same format and populates the modal + * accordingly. Note that this does NOT clear the modal but merely + * appends to the end of it. + * To clear, call {@link RedshiftModal#clear}. + * + * @param {Object[]} data - the data to populate the modal with + */ +RedshiftModal.prototype.load = function(data) { + for (var i = 0; i < data.length; ++i) { + if (i == 0) { + var lr = this.createLeftRow(); + lr.find(".redshift-modal-z").val(data[i].from); + this.grid.append(lr); + } + + var rr = this.createRightRow(); + rr.find(".redshift-modal-samples").val(data[i].points); + this.grid.append(rr); + + var lr2 = this.createLeftRow(); + lr2.find(".redshift-modal-z").val(data[i].to); + this.grid.append(lr2); + } +}; diff --git a/class/RealSpaceInterface/static/js/simulation.js b/class/RealSpaceInterface/static/js/simulation.js new file mode 100644 index 00000000..e7387247 --- /dev/null +++ b/class/RealSpaceInterface/static/js/simulation.js @@ -0,0 +1,874 @@ +/** @const {string[]} */ +var QUANTITIES = ["d_g", "d_b", "d_ur", "d_g/4 + psi", "d_cdm"]; +/** @const {string[]} */ +var QUANTITY_LABELS = [ + "δγ", + "δb", + "δν", + "δγ/4 + ψ", + "δcdm" +]; + +/** + * @typedef {Object} Simulation + * @typedef {Object} SimulationManager + * @typedef {Object} QuantityObject + */ + +/** + * Represents a single simulation. + * + * @constructor + */ +function Simulation() { + /* + These objects (once filled) can be accessed like this: + transfer[QUANTITY][FRAME][DATAPOINT] + */ + this.real = this.createQuantityObject(); + this.transfer = this.createQuantityObject(); + this.fourier = this.createQuantityObject(); + + this.params = null; + + // Cl's + this.l = null; + this.tCl = null; + + this.mPk = null; + + this.frameCount = 0; +} + +/** + * Create a new quantity object, i.e. an object whose + * keys are the quantities of {@link QUANTITIES} and values + * empty arrays. + */ +Simulation.prototype.createQuantityObject = function() { + var obj = {}; + for (var qty of QUANTITIES) { + obj[qty] = []; + } + return obj; +} + +/** + * Set the cosmological parameters associated with this simulation. + * + * @param {Object} params - The parameter object + */ +Simulation.prototype.setParameters = function(params) { + this.params = params; +}; + +/** + * Add a frame to this simulation. + * + * @param {QuantityObject} real - real data + * @param {QuantityObject} transfer - transfer function data + * @param {QuantityObject} fourier - fourier data (not used) + */ +Simulation.prototype.addFrame = function(real, transfer, fourier) { + for (var qty of QUANTITIES) { + this.real[qty].push(real[qty]); + this.transfer[qty].push(transfer[qty]); + this.fourier[qty].push(fourier[qty]); + } + this.frameCount++; +}; + +/** + * Add a frame to this simulation. + * + * @param {Float32Array} real - real data + * @param {Float32Array} transfer - transfer function data + * @param {Float32Array} fourier - fourier data (not used) + */ +Simulation.prototype.addInitial = function(real, transfer, fourier) { + for (var qty of QUANTITIES) { + this.real[qty].push(real); + this.transfer[qty].push(transfer); + this.fourier[qty].push(fourier); + } + this.frameCount++; +} + +/** + * Get the real data of `quantity` at frame `index`. + * @param {string} quantity + * @param {number} index - frame number + * @return {Float32Array} real data + */ +Simulation.prototype.getReal = function(quantity, index) { + return this.real[quantity][index]; +}; + +/** + * Get the transfer function data of `quantity` at frame `index`. + * @param {string} quantity + * @param {number} index - frame number + * @return {Float32Array} transfer function array + */ +Simulation.prototype.getTransfer = function(quantity, index) { + console.assert(index < this.transfer.length); + return this.transfer[quantity][index]; +}; + +/** + * Get the Fourier data of `quantity` at frame `index`. + * @deprecated Unused + * @param {string} quantity + * @param {number} index - frame number + * @return {Float32Array} Fourier data + */ +Simulation.prototype.getFourier = function(quantity, index) { + console.assert(index < this.fourier.length); + return this.fourier[quantity][index]; +}; + +/** + * Get the number of frames in this simulation. + * @return {number} frame count + */ +Simulation.prototype.getFrameCount = function() { + return this.frameCount; +}; + +/************************************************************************************************* +*************************************************************************************************/ + +/** + * A container class which is capable of managing multiple simulations. + * Provides an abstraction over dealing with individual simulations manually. + * + * @constructor + * @param {THREE.Texture} colorMap - A texture containing the initial color map + * + * @property {Simulation[]} simulations - An array of all stored simulations + * @property {number} frame - The currently active frame + * @property {number[]} active - The indices of active simulations + * @property {THREE.Group} planeGroup - The object group of planes in 'regular' mode + * @property {THREE.Group} collisionPlaneGroup - The group containing the meshes used + * for mouse picking + * @property {number} resolution - mesh resolution + * @property {number} PLANE_SIZE - size of planes in world space + * @property {number} PLANE_MARGIN - margin between planes in world units + * @property {number} GRID_DIVISIONS - number of grid divisions + * + * @property {THREE.Texture} colorMap - active color map + * @property {Simulation} targetSimulation - reference to the (unfinished) simulation object that is still receiving data + * + * @property {Float32Array} realInit - initial state for real data, that is the same for all quantities and passed to every newly created instance of {@link Simulation} + * @property {GridLayout} layout - layout manager which calculates the position of the individual planes + * @property {THREE.Group} activeBoxes - group of color outlines implemented as BoxHelpers + * + * @property {bool} singleMode - true if application is in single mode, i.e. all quantities of a _single_ simulation are shown side by side. false otherwise. + * @property {number} singleSimulationIndex - index of simulation that is shown in single mode (if any) + * @property {THREE.Group} singleGroup - object group of planes and grids in single mode + * @property {THREE.Mesh[]} singleMeshes - array of plane meshes in single mode + * @property {THREE.Mesh[]} singleCollisionMeshes - + * array of low resolution plane meshes in single mode used for mouse picking + * @property {THREE.Mesh[]} singleGrids - array of grids in single mode + */ +function SimulationManager(colorMap) { + this.simulations = []; + + this.frame = 0; + + this.active = []; // List of active (i.e. visible) simulations + this.planeGroup = new THREE.Group(); + this.collisionPlaneGroup = new THREE.Group(); + + // Definition of constants + this.resolution = 200; + this.PLANE_SIZE = 500; // Size of Ground Plane in world units + this.PLANE_MARGIN = 50; + this.GRID_DIVISIONS = 20; + + this.colorMap = colorMap; + + // active simulation, i.e. simulation that is (still) receiving data + this.targetSimulation = null; + + this.realInit = null; + this.transferInit = null; + this.fourierInit = null; + + this.layout = new GridLayout(1, this.PLANE_SIZE, this.PLANE_MARGIN); + + // Group of highlight boxes + this.activeBoxes = new THREE.Group(); + + // Single Mode = Showing only 1 simulation, but all 4 quantities at once + this.singleMode = false; + this.singleSimulationIndex = 0; + this.singleGroup = new THREE.Group(); + this.singleMeshes = []; + this.singleCollisionMeshes = []; + this.singleGrids = []; +} + +/** + * Test whether the user hovers over any of the simulations and react accordingly, + * i.e. create a colored outline in the appropriate color. + * If in single mode, also display the quantity of the currently hovered plane + * in the status bar. + * + * @param {THREE.Raycaster} raycaster - raycaster to be used for intersection checking + */ +SimulationManager.prototype.mousePick = function(raycaster) { + var self = this; + this.activeBoxes.children.forEach(function(box) { + self.activeBoxes.remove(box); + }); + $("#displayHover").text(""); + + if (this.singleMode) { + var intersects = raycaster.intersectObjects(this.singleCollisionMeshes); + for (var i = 0; i < intersects.length; i++) { + // Find corresponding simulation + var qtyIdx = intersects[i].object.index; + var box = new THREE.BoxHelper(this.singleCollisionMeshes[qtyIdx]); + box.material.linewidth = 5; + box.material.color = new THREE.Color(colors[qtyIdx % colors.length]); + this.activeBoxes.add(box); + $("#displayHover").html(" | " + QUANTITY_LABELS[qtyIdx]); + } + } else { + var intersects = raycaster.intersectObjects(this.getCollisionGroup().children); + for (var i = 0; i < intersects.length; i++) { + // Find corresponding simulation + var simulationIndex = intersects[i].object.index; + var simulation = simulationManager.getSimulations()[simulationIndex]; + var box = new THREE.BoxHelper(simulation.collisionMesh); + box.material.linewidth = 5; + box.material.color = new THREE.Color(colors[simulationIndex % colors.length]); + this.activeBoxes.add(box); + } + } +}; + +/** + * @return {THREE.Mesh[]} array of active boxes (colored outlines). + */ +SimulationManager.prototype.getActiveBoxes = function() { + return this.activeBoxes; +}; + +/** + * Create a new set of uniforms for the shader material for a new {@link Simulation} instance. + * @private + * @return {Object} uniform object + */ +SimulationManager.prototype.createUniforms = function() { + return { + notFlat: { + type: 'i', + value: parameterGui.config.notFlat + }, + amplitude: { + type: 'f', + value: parameterGui.config.amplitude + }, + cmap: { + type: "t", + value: this.colorMap, + }, + }; +} + +/** + * Set the resolution for future new simulations. + * @parameter {number} resolution - resolution (side length of mesh as number of vertices) + */ +SimulationManager.prototype.setResolution = function(resolution) { + // If updating, also update this.getResolution + this.resolution = resolution; + if (this.singleMode && this.singleGroup.children.length > 0 || + !this.singleMode && this.planeGroup.children.length > 0) { + console.warn("Resolution set to " + resolution + ", but there are existing planes!"); + } +}; + +/** + * @return {number} resolution + */ +SimulationManager.prototype.getResolution = function() { + return this.resolution; +}; + +/** + * Set a new color map. + * + * @param {THREE.Texture} texture - new color map to be set + */ +SimulationManager.prototype.setColorMap = function(texture) { + this.colorMap = texture; + + for (var plane of this.planeGroup.children) { + if (plane.material.uniforms) + plane.material.uniforms.cmap.value = texture; + } + for (var plane of this.singleMeshes) { + plane.material.uniforms.cmap.value = texture; + } +}; + +/** + * Create a new material for a {@link Simulation} instance. + * @private + * + * @return {THREE.ShaderMaterial} ShaderMaterial for simulation + */ +SimulationManager.prototype.createMeshMaterial = function() { + var uniforms = this.createUniforms(); + return new THREE.ShaderMaterial({ + uniforms: uniforms, + vertexShader: document.getElementById('vertexshader').textContent, + fragmentShader: document.getElementById('fragmentshader').textContent, + }); +}; + +/** + * Create a new simulation and initialize it with the stored initial state. + */ +SimulationManager.prototype.createSimulation = function() { + var sim = new Simulation(); + this.simulations.push(sim); + this.targetSimulation = sim; + sim.addInitial(this.realInit, this.transferInit, this.fourierInit); + this.activateSimulation(sim); +}; + + +/** + * @return {Simulation} the current target simulation + */ +SimulationManager.prototype.getTarget = function() { + return this.targetSimulation; +}; + +/** + * @return {bool} whether or not there exists a target simulation. + */ +SimulationManager.prototype.hasTarget = function() { + return this.targetSimulation !== null; +}; + +/** + * Finalize target (should be called once all data for a simulation has been received). + */ +SimulationManager.prototype.finalizeTarget = function() { + this.targetSimulation = null; +}; + +/** + * Destroys the current target. This should be called in case an error occurs during + * the data transfer from the server. + */ +SimulationManager.prototype.destroyTarget = function() { + this.delete(this.simulations.indexOf(this.targetSimulation)); + this.targetSimulation = null; +}; + +/** + * Update the grids after the user toggles grid visibility in the control panel. + */ +SimulationManager.prototype.updateGrids = function() { + var self = this; + if (this.singleMode) { + this.singleGrids.forEach(function(grid) { + grid.visible = parameterGui.config.showGrid; + }); + } else { + this.active.map(function(idx) { return self.simulations[idx]; }).forEach(function(sim) { + sim.grid.visible = parameterGui.config.showGrid; + }); + } +}; + +/** + * Enter single mode for the given simulation index, i.e. show all quantities + * for that simulation side by side. + * + * @param {number} simulationIdx - index of simulation to view in single mode + */ +SimulationManager.prototype.enableSingleMode = function(simulationIdx) { + this.singleMode = true; + this.singleSimulationIndex = simulationIdx; + + var self = this; + QUANTITIES.forEach(function(qty, qtyIdx) { + var plane = self.createPlane(); + var collisionPlane = self.createCollisionPlane(qtyIdx); + var grid = new THREE.GridHelper(self.PLANE_SIZE, self.GRID_DIVISIONS); + self.singleMeshes.push(plane); + self.singleCollisionMeshes.push(collisionPlane); + self.singleGrids.push(grid); + + self.singleGroup.add(plane); + self.singleGroup.add(grid); + }); + + this.refresh(); + this.loadFrame("d_g", this.frame); // Quantity is actually unused here and merely serves as a dummy +}; + +/** + * Leave single mode. + */ +SimulationManager.prototype.disableSingleMode = function() { + this.singleMode = false; + + for (var i = 0; i < this.singleGroup.children.length; ++i) { + this.singleGroup.remove(this.singleGroup.children[i]); + } + + + for (var i = 0; i < QUANTITIES.length; ++i) { + this.singleMeshes[i].geometry.dispose(); + this.singleCollisionMeshes[i].geometry.dispose(); + this.singleGrids[i].geometry.dispose(); + } + + this.singleMeshes = []; + this.singleCollisionMeshes = []; + this.singleGrids = []; + + this.refresh(); +}; + +/** + * @return {THREE.Group} {@link SimulationManager#singleGroup} + */ +SimulationManager.prototype.getSingleGroup = function() { + return this.singleGroup; +}; + +/** + * Activate the simulation for the given index. + * + * @param {number} index - index of the simulation to activate + */ +SimulationManager.prototype.activate = function(index) { + console.log("Activating simulation #" + index); + + this.active.push(index); + + this.simulations[index].mesh = this.createPlane(); + this.simulations[index].collisionMesh = this.createCollisionPlane(index); + this.simulations[index].grid = new THREE.GridHelper(this.PLANE_SIZE, this.GRID_DIVISIONS); + this.simulations[index].grid.visible = parameterGui.config.showGrid; + + this.planeGroup.add(this.simulations[index].mesh); + this.planeGroup.add(this.simulations[index].grid); + this.collisionPlaneGroup.add(this.simulations[index].collisionMesh); + + this.refresh(); +}; + +/** + * Activate the given simulation. + * + * @param {Simulation} sim - simulation to activate + */ +SimulationManager.prototype.activateSimulation = function(sim) { + this.activate(this.simulations.indexOf(sim)); +}; + +/** + * Deactivate the simulation for the given index. + * + * @param {number} index - index of simulation to deactivate + */ +SimulationManager.prototype.deactivate = function(index) { + if (!this.active.includes(index)) { + return; + } + this.active.splice(this.active.indexOf(index), 1); + var simulation = this.simulations[index]; + + // Remove meshes from rendering groups + this.planeGroup.remove(simulation.mesh); + this.planeGroup.remove(simulation.grid); + this.collisionPlaneGroup.remove(simulation.collisionMesh); + + // Dispose of mesh geometry + if (simulation.mesh) { + simulation.mesh.geometry.dispose(); + simulation.mesh.material.dispose(); + simulation.mesh = null; + } + if (simulation.collisionMesh) { + simulation.collisionMesh.geometry.dispose(); + simulation.collisionMesh = null; + } + if (simulation.grid) { + simulation.grid.geometry.dispose(); + simulation.grid = null; + } + + this.refresh(); +}; + +/** + * Deactivate given simulation. + * + * @param {Simulation} sim - simulation to deactivate + */ +SimulationManager.prototype.deactivateSimulation = function(sim) { + this.deactivate(this.simulations.indexOf(sim)); +}; + +/** + * Delete all simulations. + */ +SimulationManager.prototype.deleteAll = function() { + // for (var activeIdx of this.active) { + // this.deactivate(activeIdx); + // } + + // Evaluate count outside for loop since loop body modifies this.simulations + var count = this.simulations.length; + for (var i = 0; i < count; ++i) { + // Always delete simulation at index #0, since by deleting simulation #0, + // what was previously simulation #1 now becomes #0. + this.delete(0); + } + + this.active = []; + this.simulations = []; + console.assert(this.planeGroup.children.length == 0); + this.refresh(); +}; + +/** + * Delete a single simulation. + * + * @param {number} index of simulation to delete. + */ +SimulationManager.prototype.delete = function(index) { + if (index >= 0 && index < this.simulations.length) { + this.deactivate(index); + + // Since a simulation was removed from the list, + // the indices of this.active aren't accurate anymore. + // Every active index > `index` (i.e. the index of the simulation + // to delete) needs to be shifted down by one so that they continue + // to refer to the correct simulation. + this.active = this.active.map(function(idx) { + return (idx > index) ? idx - 1 : idx; + }); + + // After this, no more reference the simulation should exist + this.simulations.splice(index, 1); + + // Update simulationIndex on collision meshes + this.simulations.forEach(function(simulation, index) { + if (simulation.collisionMesh) { + simulation.collisionMesh.index = index; + } + }); + } +}; + +/** + * Needs to be called after simulations have been activated/deactivated + * to re-layout the remaining (activated) planes. + */ +SimulationManager.prototype.refresh = function() { + if (this.singleMode) { + this.layout.count = QUANTITIES.length; + this.layout.recalculate(); + + for (var i = 0; i < QUANTITIES.length; ++i) { + var position = this.layout.getWorldPosition(i); + this.singleMeshes[i].position.x = position[0]; + this.singleMeshes[i].position.z = position[1]; + this.singleCollisionMeshes[i].position.x = position[0]; + this.singleCollisionMeshes[i].position.z = position[1]; + this.singleGrids[i].position.x = position[0]; + this.singleGrids[i].position.z = position[1]; + } + } else { + this.layout.count = this.active.length; + this.layout.recalculate(); + + var self = this; + var objects = ["mesh", "collisionMesh", "grid"]; + this.active.forEach(function(active, gridIdx) { + var position = self.layout.getWorldPosition(gridIdx); + var x = position[0]; + var y = position[1]; + + var sim = self.simulations[active]; + objects.forEach(function(obj) { + sim[obj].position.x = x; + sim[obj].position.z = y; + }); + }); + } +}; + +/** + * Create a new mesh for a simulation. + * @private + * @return {THREE.Mesh} mesh + */ +SimulationManager.prototype.createPlane = function() { + + var bufferGeometry = new THREE.PlaneBufferGeometry( + this.PLANE_SIZE, this.PLANE_SIZE, + this.resolution - 1, this.resolution - 1 + ); + var result = new THREE.Mesh(bufferGeometry, this.createMeshMaterial()); + + var displacementBuffer = new Float32Array(this.resolution * this.resolution); + var displacementAttribute = new THREE.BufferAttribute(displacementBuffer, 1); + result.geometry.addAttribute("displacement", displacementAttribute); + result.rotation.x = -Math.PI/2; + + return result; +}; + +/** + * Create a plane for mouse hover checking for the simulation at given index. + * + * @param {number} index - index of simulation + */ +SimulationManager.prototype.createCollisionPlane = function(index) { + // index is required, as it is stored as mesh attribute to allow the + // mouse picker to identify the simulation that is associated with the collision mesh. + var bufferGeometry = new THREE.PlaneBufferGeometry(this.PLANE_SIZE, this.PLANE_SIZE); + var result = new THREE.Mesh(bufferGeometry); + result.rotation.x = -Math.PI/2; + // Apply transformation such that ray caster detects plane in correct orientation + // even if it is not added to the scene + result.updateMatrix(); + result.geometry.applyMatrix(result.matrix); + result.rotation.set(0, 0, 0); + result.updateMatrix(); + result.index = index; + return result; +}; + +/** + * @return {Simulation[]} {@link SimulationManager#simulations} + */ +SimulationManager.prototype.getSimulations = function() { + return this.simulations; +}; + +/** + * @return {number[]} {@link SimulationManager#active} + */ +SimulationManager.prototype.getActive = function() { + return this.active; +}; + +/** + * Return a list of active simulations as tuples, each of which consists of the + * index of the simulation and the simulation itself. + * @return {Object[]} + */ +SimulationManager.prototype.getActiveSimulations = function() { + var self = this; + return this.active.map(function(idx) { return [idx, self.simulations[idx]]; }); +}; + +/** + * @callback SimulationManager~activeCallback + * @param {number} activeIndex + * @param {Simulation} activeSimulation + */ + +/** + * Iterate over active simulations. + * + * @param {SimulationManager~activeCallback} - a function called for each active simulation + */ +SimulationManager.prototype.forEachActive = function(callback) { + var self = this; + this.active.forEach(function(activeIndex) { + callback(activeIndex, self.simulations[activeIndex]); + }); +} + +/** + * Check whether a given simulation specified by index is active. + * + * @param {number} index - index of simulation + */ +SimulationManager.prototype.isActive = function(index) { + return this.active.includes(index); +}; + +/** + * Update meshes to show the given frame for the given quantity. + * + * @param {string} quantity - quantity to display + * @param {number} frame - frame to display + */ +SimulationManager.prototype.loadFrame = function(quantity, frame) { + this.frame = frame; + + if (this.singleMode) { + this.loadSingleFrame(frame); + } else { + var self = this; + this.active.forEach(function(index) { + self.loadFrameForIndex(quantity, index, frame); + }); + } +}; + +/** + * Similar to {@link SimulationManager#loadFrame}, but for single mode (i.e. + * all quantities). + * + * @param {number} frame - frame to load + */ +SimulationManager.prototype.loadSingleFrame = function(frame) { + var self = this; + QUANTITIES.forEach(function(qty, qtyIdx) { + var disp = self.singleMeshes[qtyIdx].geometry.attributes.displacement; + disp.array = self.simulations[self.singleSimulationIndex].getReal(qty, frame); + disp.needsUpdate = true; + }); +}; + +/** + * Load the given frame for the given quantity for the given simulation index. + * + * @private + * @param {string} quantity - quantity + * @param {number} index - simulation index + * @param {number} frame - frame + */ +SimulationManager.prototype.loadFrameForIndex = function(quantity, index, frame) { + var simulation = this.simulations[index]; + var plane = simulation.mesh; + + // Update plane + var displacementArray = plane.geometry.attributes.displacement.array; + var newArray = simulation.getReal(quantity, frame); + console.assert(newArray.length === plane.geometry.attributes.displacement.array.length); + plane.geometry.attributes.displacement.array = newArray; + plane.geometry.attributes.displacement.needsUpdate = true; +}; + +/** + * Check whether there already exists a simulation for the given set of cosmological parameters. + * + * @param {Object} cosmoParams - object of cosmological parameters + * @return {bool} + */ +SimulationManager.prototype.wasAlreadySimulated = function(cosmoParams) { + for (var simulation of this.simulations) { + // Require that cosmo params have already been set. + // This is not the case for the first simulation. + if (simulation.params) { + var sProps = Object.getOwnPropertyNames(simulation.params); + var nProps = Object.getOwnPropertyNames(cosmoParams); + + var lengthMatch = sProps.length == nProps.length; + var propMatch = true; + + for (var i = 0; i < sProps.length; i++) { + var pName = sProps[i]; + if (simulation.params[pName] !== cosmoParams[pName]) { + propMatch = false; + break; + } + } + + if (lengthMatch && propMatch) { + return true; + } + } + } + return false; +}; + +/** + * Get number of frames. + * @return {number} frame count + */ +SimulationManager.prototype.getFrameCount = function() { + if (this.simulations.length > 0) + return this.simulations[0].getFrameCount(); + else + return 0; +}; + +/** + * @return {THREE.Group} {@link SimulationManager#planeGroup} + */ +SimulationManager.prototype.getGroup = function() { + return this.planeGroup; +}; + +/** + * @return {THREE.Group} {@link SimulationManager#collisionPlaneGroup} + */ +SimulationManager.prototype.getCollisionGroup = function() { + return this.collisionPlaneGroup; +}; + +/** + * Set a uniform value for all materials. + * + * @param {string} key - uniform key + * @param {Object} value - value for key + */ +SimulationManager.prototype.setUniform = function(key, value) { + var self = this; + if (this.singleMode) { + this.singleMeshes.forEach(function(mesh) { + mesh.material.uniforms[key].value = value; + }); + } else { + this.active.forEach(function(idx) { + var simulation = self.simulations[idx]; + if (simulation.mesh) { + simulation.mesh.material.uniforms[key].value = value; + } + }); + } +}; + +/** + * Get transfer function arrays of all simulations for given quantity and frame. + * + * @param {string} quantity + * @param {number} frame + * + * @return {Float32Array[]} array of transfer function data for all simulations + */ +SimulationManager.prototype.getTransferData = function(quantity, frame) { + var self = this; + return this.active.map(function(idx) { return self.simulations[idx].transfer[quantity][frame]; }); +}; + +/** + * Get transfer function data for given quantity and frame of active single-mode simulation. + * + * @param {string} quantity + * @param {number} frame + * + * @return {Float32Array} + */ +SimulationManager.prototype.getTransferDataOfSingle = function(quantity, frame) { + var self = this; + return self.simulations[self.singleSimulationIndex].transfer[quantity][frame]; +}; + +/** + * Get index and simulation itself of currently active single mode simulation. + * + * @return {Object[]} + */ +SimulationManager.prototype.getSingleSimulation = function() { + return [this.singleSimulationIndex, this.simulations[this.singleSimulationIndex]]; +}; diff --git a/class/RealSpaceInterface/static/js/simulationList.js b/class/RealSpaceInterface/static/js/simulationList.js new file mode 100644 index 00000000..3381a5c2 --- /dev/null +++ b/class/RealSpaceInterface/static/js/simulationList.js @@ -0,0 +1,337 @@ +/** + * Number of decimal digits to round values to in the simulation list dialog. + * @const + * @type {number} + */ +const SIMU_LIST_ROUNDING = 3; + +/** + * Will be called when a simulation is deleted. + * + * @callback SimuTable~deleteCallback + * @param {number} index - index of simulation to be deleted + */ + +/** + * Will be called when a simulation is activated. + * + * @callback SimuTable~activateCallback + * @param {number} index - index of simulation to be activated + */ + +/** + * Will be called when a simulation is deactivated. + * @callback SimuTable~deactivateCallback + * @param {number} index - index of simulation to be deactivated + */ + +/** + * Will be called when a .gif needs to be created for a simulation. + * @callback SimuTable~gifCallback + * @param {number} index - index of simulation to create a .gif of + */ + +/** + * Will be called when an image needs to be created for a simulation at the current frame. + * @callback SimuTable~imageCallback + * @param {number} index - index of simulation to create an image of + */ + +/** + * Will be called when user requests simulation to be displayed in 'single' mode + * @callback SimuTable~singleModeCallback + * @param {number} index - index of simulation to display in single mode + */ + +/** + * Will be called when user requests camera to be focused on a simulation. + * @callback SimuTable~focusCameraCallback + * @param {number} index - index of simulation to focus in view + */ + +/** + * Will be called when user requests to load parameters of simulation + * into control panel. + * @callback SimuTable~loadParamCallback + * @param {number} index - index of simulation of which to load parameters + */ + +/** + * + * Implementation of a list dialog which displays previously run simulations + * along with their respective set of cosmological parameters. + * Exposes additional functionality such as hiding and showing individual + * simulations, entering 'single' mode, in which only a single simulation + * (but all quantities of that simulation) are shown, creating a .gif and + * deleting a simulation from memory. + * The passed callbacks are bound to the appropriate buttons and actions. + * + * @constructor + * + * @param {SimuTable~deleteCallback} deleteCallback + * @param {SimuTable~activateCallback} activateCallback + * @param {SimuTable~deactivateCallback} deactivateCallback + * @param {SimuTable~gifCallback} gifCallback + * @param {SimuTable~imageCallback} imageCallback + * @param {SimuTable~singleModeCallback} singleModeCallback + * @param {SimuTable~focusCameraCallback} focusCameraCallback + * @param {SimuTable~loadParamCallback} loadParamCallback + */ +function SimuTable(deleteCallback, activateCallback, deactivateCallback, + gifCallback, imageCallback, singleModeCallback, focusCameraCallback, + loadParamCallback) { + this.deleteCallback = deleteCallback; + this.activateCallback = activateCallback; + this.deactivateCallback = deactivateCallback; + this.gifCallback = gifCallback; + this.imageCallback = imageCallback; + this.singleModeCallback = singleModeCallback; + this.focusCameraCallback = focusCameraCallback; + this.loadParamCallback = loadParamCallback; + + this.table = document.getElementById("simulationTable"); + this.tableHead = document.getElementById("simulationTableHead"); + this.tableBody = document.getElementById("simulationTableBody"); + this.rowTemplate = document.getElementById("simulationTableRowTemplate"); + + this.activeSet = 0; + + this.displayParams = ["omega_b", "omega_m", "Omega_k", "N_ur", "w0_fld", "wa_fld"]; + this.displayLabels = ["ωb", "ωm", "Ωk", + "Nur", "w0,fld", "wa,fld"]; +} + +/** + * Creates the table header for the modal. + * Reads table column headings from {@link COSMOLOGICAL_PARAMETER_LIST}. + * + */ +SimuTable.prototype.createHeader = function() { + var headRow = document.createElement("tr"); + + var activeTh = document.createElement("th"); + activeTh.textContent = "Active"; + headRow.appendChild(activeTh); + + var idxTh = document.createElement("th"); + idxTh.textContent = "#"; + idxTh.setAttribute("scope", "col"); + + headRow.appendChild(idxTh); + + for (var entry of COSMOLOGICAL_PARAMETER_LIST) { + var th = document.createElement("th"); + th.innerHTML = entry.displayName; + headRow.appendChild(th); + } + + var actionsTh = document.createElement("th"); + actionsTh.textContent = "Actions"; + + var colorTh = document.createElement("th"); + colorTh.textContent = "Color"; + + headRow.appendChild(actionsTh); + headRow.appendChild(colorTh); + + this.tableHead.appendChild(headRow); +} + +/** + * Given a list of simulations and a list of active simulations, + * populates the dialog with their data. + * + * @param {Simulation[]} simulations - list of all simulations + * @param {number[]} activeList - array of indices of active simulations. + * required to determine whether to show + * individual simulations as active or + * inactive. + */ +SimuTable.prototype.populate = function(simulations, activeList) { + var self = this; + // Data + simulations.forEach(function(sim, i) { + var isActive = activeList.includes(i); + + var sim = simulations[i]; + var row = document.createElement("tr"); + row.setAttribute("scope", "row"); + row.classList.toggle("table-primary", isActive); + + // Active checkbox + var checkbox = document.createElement("input"); + checkbox.setAttribute("type", "checkbox"); + checkbox.classList.add("visible-checkbox"); + + checkbox.onclick = function() { + row.classList.toggle("table-primary"); + if (checkbox.checked) { + self.activateCallback(i); + } else { + self.deactivateCallback(i); + } + }; + var checkboxTd = document.createElement("td"); + checkbox.checked = isActive; + checkboxTd.appendChild(checkbox); + row.appendChild(checkboxTd); + + // Index + var idxCol = document.createElement("td"); + idxCol.textContent = i; + row.appendChild(idxCol); + + for (var entry of COSMOLOGICAL_PARAMETER_LIST) { + var td = document.createElement("td"); + td.textContent = round(sim.params[entry.name], 3); + row.appendChild(td); + } + + /* BUTTONS */ + var buttonGroup = document.createElement("div"); + buttonGroup.classList.add("btn-group", "btn-group-sm"); + + // Expand in Single Mode Button + var singleModeButton = document.createElement("button"); + singleModeButton.classList.add("btn", "btn-primary", "simulationTableSingleModeBtn"); + var singleIconSpan = document.createElement("span"); + singleIconSpan.classList.add("oi", "oi-layers"); + singleModeButton.appendChild(singleIconSpan); + singleModeButton.onclick = function() { + self.singleModeCallback(i); + }; + singleModeButton.setAttribute("data-toggle", "tooltip"); + singleModeButton.setAttribute("data-placement", "top"); + singleModeButton.setAttribute("title", "Show all quantities side by side"); + buttonGroup.appendChild(singleModeButton); + + // Image Button + var imgButton = document.createElement("button"); + imgButton.classList.add("btn", "btn-success", "simulationTableImgBtn"); + var imgIconSpan = document.createElement("span"); + imgIconSpan.classList.add("oi", "oi-image"); + imgButton.appendChild(imgIconSpan); + imgButton.onclick = function() { + self.imageCallback(i); + }; + imgButton.setAttribute("data-toggle", "tooltip"); + imgButton.setAttribute("data-placement", "top"); + imgButton.setAttribute("title", "Take Snapshot"); + buttonGroup.appendChild(imgButton); + + // GIF Button + var gifButton = document.createElement("button"); + gifButton.classList.add("btn", "btn-success", "simulationTableGifBtn"); + var gifIconSpan = document.createElement("span"); + gifIconSpan.classList.add("oi", "oi-video"); + gifButton.appendChild(gifIconSpan); + gifButton.onclick = function() { + self.gifCallback(i); + }; + gifButton.setAttribute("data-toggle", "tooltip"); + gifButton.setAttribute("data-placement", "top"); + gifButton.setAttribute("title", "Create .gif"); + buttonGroup.appendChild(gifButton); + + // Load Parameters Button + var loadParamButton = document.createElement("button"); + loadParamButton.classList.add("btn", "btn-secondary", + "simulationTableLoadParamBtn"); + var paramIconSpan = document.createElement("span"); + paramIconSpan.classList.add("oi", "oi-list-rich"); + loadParamButton.appendChild(paramIconSpan); + loadParamButton.onclick = function() { + self.loadParamCallback(i); + }; + loadParamButton.setAttribute("data-toggle", "tooltip"); + loadParamButton.setAttribute("data-placement", "top"); + loadParamButton.setAttribute("title", "Load Parameters in Control Panel"); + buttonGroup.appendChild(loadParamButton); + + // Focus Camera Button + var focusCameraButton = document.createElement("button"); + focusCameraButton.classList.add("btn", "btn-secondary", "simulationTableFocusCameraBtn"); + var focusIconSpan = document.createElement("span"); + focusIconSpan.classList.add("oi", "oi-aperture"); + focusCameraButton.appendChild(focusIconSpan); + focusCameraButton.onclick = function() { + self.focusCameraCallback(i); + }; + focusCameraButton.setAttribute("data-toggle", "tooltip"); + focusCameraButton.setAttribute("data-placement", "top"); + focusCameraButton.setAttribute("title", "Focus in View"); + buttonGroup.appendChild(focusCameraButton); + + // Delete Button + var deleteButton = document.createElement("button"); + deleteButton.classList.add("btn", "btn-danger", "simulationTableDelBtn"); + var deleteIconSpan = document.createElement("span"); + deleteIconSpan.classList.add("oi", "oi-x"); + deleteButton.appendChild(deleteIconSpan); + deleteButton.onclick = function() { + self.deleteCallback(i); + }; + deleteButton.setAttribute("data-toggle", "tooltip"); + deleteButton.setAttribute("data-placement", "top"); + deleteButton.setAttribute("title", "Delete (cannot be undone!)"); + buttonGroup.appendChild(deleteButton); + + + var buttonTd = document.createElement("td"); + buttonTd.appendChild(buttonGroup); + row.appendChild(buttonTd); + + + // Color + var colorCircleTd = document.createElement("td"); + colorCircleTd.classList.add("color-circle-container"); + var colorCircle = document.createElement("div"); + colorCircleTd.appendChild(colorCircle); + colorCircle.classList.add("color-circle"); + colorCircle.style.backgroundColor = colors[i % colors.length]; + + row.appendChild(colorCircleTd); + + + self.tableBody.appendChild(row); + }); + + $(function () { + $('[data-toggle="tooltip"]').tooltip() + }); + +}; + +/** + * Activate a given simulation. + * + * @param {number} idx - index of simulation to active + * @deprecated + * @ignore + */ +SimuTable.prototype.setActive = function(idx) { + if (this.activeSet >= 0) { + this.tableBody.children[this.activeSet].classList.remove("table-primary"); + this.activeSet = idx; + this.tableBody.children[this.activeSet].classList.add("table-primary"); + } +} + +/** + * Clears all rows. + */ +SimuTable.prototype.clear = function() { + while (this.tableBody.firstChild) { + this.tableBody.removeChild(this.tableBody.firstChild); + } +} + +/** + * Refreshes (i.e. clears and repopulates). + * @deprecated + * @ignore + */ +SimuTable.prototype.refresh = function() { + this.clear(); + this.populate(); +} diff --git a/class/RealSpaceInterface/static/js/sockjs.min.js b/class/RealSpaceInterface/static/js/sockjs.min.js new file mode 100644 index 00000000..19b2b7eb --- /dev/null +++ b/class/RealSpaceInterface/static/js/sockjs.min.js @@ -0,0 +1,28 @@ +/* SockJS client, version 0.3.4, http://sockjs.org, MIT License + +Copyright (c) 2011-2012 VMware, Inc. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +*/ + +// JSON2 by Douglas Crockford (minified). +var JSON;JSON||(JSON={}),function(){function str(a,b){var c,d,e,f,g=gap,h,i=b[a];i&&typeof i=="object"&&typeof i.toJSON=="function"&&(i=i.toJSON(a)),typeof rep=="function"&&(i=rep.call(b,a,i));switch(typeof i){case"string":return quote(i);case"number":return isFinite(i)?String(i):"null";case"boolean":case"null":return String(i);case"object":if(!i)return"null";gap+=indent,h=[];if(Object.prototype.toString.apply(i)==="[object Array]"){f=i.length;for(c=0;c1?this._listeners[a]=d.slice(0,e).concat(d.slice(e+1)):delete this._listeners[a];return}return},d.prototype.dispatchEvent=function(a){var b=a.type,c=Array.prototype.slice.call(arguments,0);this["on"+b]&&this["on"+b].apply(this,c);if(this._listeners&&b in this._listeners)for(var d=0;d=3e3&&a<=4999},c.countRTO=function(a){var b;return a>100?b=3*a:b=a+200,b},c.log=function(){b.console&&console.log&&console.log.apply&&console.log.apply(console,arguments)},c.bind=function(a,b){return a.bind?a.bind(b):function(){return a.apply(b,arguments)}},c.flatUrl=function(a){return a.indexOf("?")===-1&&a.indexOf("#")===-1},c.amendUrl=function(b){var d=a.location;if(!b)throw new Error("Wrong url for SockJS");if(!c.flatUrl(b))throw new Error("Only basic urls are supported in SockJS");return b.indexOf("//")===0&&(b=d.protocol+b),b.indexOf("/")===0&&(b=d.protocol+"//"+d.host+b),b=b.replace(/[/]+$/,""),b},c.arrIndexOf=function(a,b){for(var c=0;c=0},c.delay=function(a,b){return typeof a=="function"&&(b=a,a=0),setTimeout(b,a)};var i=/[\\\"\x00-\x1f\x7f-\x9f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,j={"\0":"\\u0000","\x01":"\\u0001","\x02":"\\u0002","\x03":"\\u0003","\x04":"\\u0004","\x05":"\\u0005","\x06":"\\u0006","\x07":"\\u0007","\b":"\\b","\t":"\\t","\n":"\\n","\x0b":"\\u000b","\f":"\\f","\r":"\\r","\x0e":"\\u000e","\x0f":"\\u000f","\x10":"\\u0010","\x11":"\\u0011","\x12":"\\u0012","\x13":"\\u0013","\x14":"\\u0014","\x15":"\\u0015","\x16":"\\u0016","\x17":"\\u0017","\x18":"\\u0018","\x19":"\\u0019","\x1a":"\\u001a","\x1b":"\\u001b","\x1c":"\\u001c","\x1d":"\\u001d","\x1e":"\\u001e","\x1f":"\\u001f",'"':'\\"',"\\":"\\\\","\x7f":"\\u007f","\x80":"\\u0080","\x81":"\\u0081","\x82":"\\u0082","\x83":"\\u0083","\x84":"\\u0084","\x85":"\\u0085","\x86":"\\u0086","\x87":"\\u0087","\x88":"\\u0088","\x89":"\\u0089","\x8a":"\\u008a","\x8b":"\\u008b","\x8c":"\\u008c","\x8d":"\\u008d","\x8e":"\\u008e","\x8f":"\\u008f","\x90":"\\u0090","\x91":"\\u0091","\x92":"\\u0092","\x93":"\\u0093","\x94":"\\u0094","\x95":"\\u0095","\x96":"\\u0096","\x97":"\\u0097","\x98":"\\u0098","\x99":"\\u0099","\x9a":"\\u009a","\x9b":"\\u009b","\x9c":"\\u009c","\x9d":"\\u009d","\x9e":"\\u009e","\x9f":"\\u009f","\xad":"\\u00ad","\u0600":"\\u0600","\u0601":"\\u0601","\u0602":"\\u0602","\u0603":"\\u0603","\u0604":"\\u0604","\u070f":"\\u070f","\u17b4":"\\u17b4","\u17b5":"\\u17b5","\u200c":"\\u200c","\u200d":"\\u200d","\u200e":"\\u200e","\u200f":"\\u200f","\u2028":"\\u2028","\u2029":"\\u2029","\u202a":"\\u202a","\u202b":"\\u202b","\u202c":"\\u202c","\u202d":"\\u202d","\u202e":"\\u202e","\u202f":"\\u202f","\u2060":"\\u2060","\u2061":"\\u2061","\u2062":"\\u2062","\u2063":"\\u2063","\u2064":"\\u2064","\u2065":"\\u2065","\u2066":"\\u2066","\u2067":"\\u2067","\u2068":"\\u2068","\u2069":"\\u2069","\u206a":"\\u206a","\u206b":"\\u206b","\u206c":"\\u206c","\u206d":"\\u206d","\u206e":"\\u206e","\u206f":"\\u206f","\ufeff":"\\ufeff","\ufff0":"\\ufff0","\ufff1":"\\ufff1","\ufff2":"\\ufff2","\ufff3":"\\ufff3","\ufff4":"\\ufff4","\ufff5":"\\ufff5","\ufff6":"\\ufff6","\ufff7":"\\ufff7","\ufff8":"\\ufff8","\ufff9":"\\ufff9","\ufffa":"\\ufffa","\ufffb":"\\ufffb","\ufffc":"\\ufffc","\ufffd":"\\ufffd","\ufffe":"\\ufffe","\uffff":"\\uffff"},k=/[\x00-\x1f\ud800-\udfff\ufffe\uffff\u0300-\u0333\u033d-\u0346\u034a-\u034c\u0350-\u0352\u0357-\u0358\u035c-\u0362\u0374\u037e\u0387\u0591-\u05af\u05c4\u0610-\u0617\u0653-\u0654\u0657-\u065b\u065d-\u065e\u06df-\u06e2\u06eb-\u06ec\u0730\u0732-\u0733\u0735-\u0736\u073a\u073d\u073f-\u0741\u0743\u0745\u0747\u07eb-\u07f1\u0951\u0958-\u095f\u09dc-\u09dd\u09df\u0a33\u0a36\u0a59-\u0a5b\u0a5e\u0b5c-\u0b5d\u0e38-\u0e39\u0f43\u0f4d\u0f52\u0f57\u0f5c\u0f69\u0f72-\u0f76\u0f78\u0f80-\u0f83\u0f93\u0f9d\u0fa2\u0fa7\u0fac\u0fb9\u1939-\u193a\u1a17\u1b6b\u1cda-\u1cdb\u1dc0-\u1dcf\u1dfc\u1dfe\u1f71\u1f73\u1f75\u1f77\u1f79\u1f7b\u1f7d\u1fbb\u1fbe\u1fc9\u1fcb\u1fd3\u1fdb\u1fe3\u1feb\u1fee-\u1fef\u1ff9\u1ffb\u1ffd\u2000-\u2001\u20d0-\u20d1\u20d4-\u20d7\u20e7-\u20e9\u2126\u212a-\u212b\u2329-\u232a\u2adc\u302b-\u302c\uaab2-\uaab3\uf900-\ufa0d\ufa10\ufa12\ufa15-\ufa1e\ufa20\ufa22\ufa25-\ufa26\ufa2a-\ufa2d\ufa30-\ufa6d\ufa70-\ufad9\ufb1d\ufb1f\ufb2a-\ufb36\ufb38-\ufb3c\ufb3e\ufb40-\ufb41\ufb43-\ufb44\ufb46-\ufb4e\ufff0-\uffff]/g,l,m=JSON&&JSON.stringify||function(a){return i.lastIndex=0,i.test(a)&&(a=a.replace(i,function(a){return j[a]})),'"'+a+'"'},n=function(a){var b,c={},d=[];for(b=0;b<65536;b++)d.push(String.fromCharCode(b));return a.lastIndex=0,d.join("").replace(a,function(a){return c[a]="\\u"+("0000"+a.charCodeAt(0).toString(16)).slice(-4),""}),a.lastIndex=0,c};c.quote=function(a){var b=m(a);return k.lastIndex=0,k.test(b)?(l||(l=n(k)),b.replace(k,function(a){return l[a]})):b};var o=["websocket","xdr-streaming","xhr-streaming","iframe-eventsource","iframe-htmlfile","xdr-polling","xhr-polling","iframe-xhr-polling","jsonp-polling"];c.probeProtocols=function(){var a={};for(var b=0;b0&&h(a)};return c.websocket!==!1&&h(["websocket"]),d["xhr-streaming"]&&!c.null_origin?e.push("xhr-streaming"):d["xdr-streaming"]&&!c.cookie_needed&&!c.null_origin?e.push("xdr-streaming"):h(["iframe-eventsource","iframe-htmlfile"]),d["xhr-polling"]&&!c.null_origin?e.push("xhr-polling"):d["xdr-polling"]&&!c.cookie_needed&&!c.null_origin?e.push("xdr-polling"):h(["iframe-xhr-polling","jsonp-polling"]),e};var p="_sockjs_global";c.createHook=function(){var a="a"+c.random_string(8);if(!(p in b)){var d={};b[p]=function(a){return a in d||(d[a]={id:a,del:function(){delete d[a]}}),d[a]}}return b[p](a)},c.attachMessage=function(a){c.attachEvent("message",a)},c.attachEvent=function(c,d){typeof b.addEventListener!="undefined"?b.addEventListener(c,d,!1):(a.attachEvent("on"+c,d),b.attachEvent("on"+c,d))},c.detachMessage=function(a){c.detachEvent("message",a)},c.detachEvent=function(c,d){typeof b.addEventListener!="undefined"?b.removeEventListener(c,d,!1):(a.detachEvent("on"+c,d),b.detachEvent("on"+c,d))};var q={},r=!1,s=function(){for(var a in q)q[a](),delete q[a]},t=function(){if(r)return;r=!0,s()};c.attachEvent("unload",t),c.unload_add=function(a){var b=c.random_string(8);return q[b]=a,r&&c.delay(s),b},c.unload_del=function(a){a in q&&delete q[a]},c.createIframe=function(b,d){var e=a.createElement("iframe"),f,g,h=function(){clearTimeout(f);try{e.onload=null}catch(a){}e.onerror=null},i=function(){e&&(h(),setTimeout(function(){e&&e.parentNode.removeChild(e),e=null},0),c.unload_del(g))},j=function(a){e&&(i(),d(a))},k=function(a,b){try{e&&e.contentWindow&&e.contentWindow.postMessage(a,b)}catch(c){}};return e.src=b,e.style.display="none",e.style.position="absolute",e.onerror=function(){j("onerror")},e.onload=function(){clearTimeout(f),f=setTimeout(function(){j("onload timeout")},2e3)},a.body.appendChild(e),f=setTimeout(function(){j("timeout")},15e3),g=c.unload_add(i),{post:k,cleanup:i,loaded:h}},c.createHtmlfile=function(a,d){var e=new ActiveXObject("htmlfile"),f,g,i,j=function(){clearTimeout(f)},k=function(){e&&(j(),c.unload_del(g),i.parentNode.removeChild(i),i=e=null,CollectGarbage())},l=function(a){e&&(k(),d(a))},m=function(a,b){try{i&&i.contentWindow&&i.contentWindow.postMessage(a,b)}catch(c){}};e.open(),e.write(' + + + + + + + + + + + + + + + + + + + + + + + + + {% block threejs %} + {% end %} + + + + + + + + + + + + {% include "SimulationList.html" %} + {% include "ProgressModal.html" %} + {% include "AlreadySimulatedModal.html" %} + {% include "GifExportModal.html" %} + {% include "ImageExportModal.html" %} + {% include "ExceptionModal.html" %} + {% include "RedshiftModal.html" %} + + {% block body %} + {% end %} + + diff --git a/class/RealSpaceInterface/templates/ImageExportModal.html b/class/RealSpaceInterface/templates/ImageExportModal.html new file mode 100644 index 00000000..6ffd11af --- /dev/null +++ b/class/RealSpaceInterface/templates/ImageExportModal.html @@ -0,0 +1,49 @@ + + diff --git a/class/RealSpaceInterface/templates/ProgressModal.html b/class/RealSpaceInterface/templates/ProgressModal.html new file mode 100644 index 00000000..8d7a6ac3 --- /dev/null +++ b/class/RealSpaceInterface/templates/ProgressModal.html @@ -0,0 +1,28 @@ + + + diff --git a/class/RealSpaceInterface/templates/RSI.html b/class/RealSpaceInterface/templates/RSI.html new file mode 100644 index 00000000..bc0da323 --- /dev/null +++ b/class/RealSpaceInterface/templates/RSI.html @@ -0,0 +1,180 @@ +{% extends "Header.html" %} + + {% block body %} + +
+ +
+
+
+
+
+
+ +
+ +
+
+
+ + + + +
+
+ + +
+ Division Size: N/A +
+
+ +
+
+
+
+
+ + About + + + + + {% end %} + + {% block threejs %} + + + + + + + + + + + + + + + + + + + + + + + + + + + + {% end %} diff --git a/class/RealSpaceInterface/templates/RedshiftModal.html b/class/RealSpaceInterface/templates/RedshiftModal.html new file mode 100644 index 00000000..71b74e51 --- /dev/null +++ b/class/RealSpaceInterface/templates/RedshiftModal.html @@ -0,0 +1,57 @@ + + + + + diff --git a/class/RealSpaceInterface/templates/SimulationList.html b/class/RealSpaceInterface/templates/SimulationList.html new file mode 100644 index 00000000..b3db40c0 --- /dev/null +++ b/class/RealSpaceInterface/templates/SimulationList.html @@ -0,0 +1,19 @@ + + diff --git a/class/RealSpaceInterface/templates/index.html b/class/RealSpaceInterface/templates/index.html new file mode 100644 index 00000000..29a0aadd --- /dev/null +++ b/class/RealSpaceInterface/templates/index.html @@ -0,0 +1,14 @@ + + + + three.js webgl - geometry - dynamic + + + + + +
+ + + + diff --git a/class/RealSpaceInterface/tornadoserver.py b/class/RealSpaceInterface/tornadoserver.py new file mode 100644 index 00000000..04d5d937 --- /dev/null +++ b/class/RealSpaceInterface/tornadoserver.py @@ -0,0 +1,248 @@ +from Calc2D.CalculationClass import Calculation + +import time +import numpy as np +from concurrent.futures import ThreadPoolExecutor +from tornado.ioloop import IOLoop +from tornado import gen +import tornado.web +import tornado.websocket +import os +import os.path +import json +import unicodedata +import logging +import base64 +import traceback +import sys + +import config + +pool = ThreadPoolExecutor(max_workers=config.MAX_THREADPOOL_WORKERS) + +def generate_redshifts(redshift_config): + logging.info(redshift_config) + arrs = [] + for conf in redshift_config: + log = conf["log"] + func = np.logspace if log else np.linspace + start = np.log10(conf["from"]) if log else conf["from"] + stop = np.log10(conf["to"]) if log else conf["to"] + arrs.append(func(start, stop, conf["points"])) + # Remove duplicates + return np.flip(np.unique(np.concatenate(arrs)), axis=0) + +# Load available colormaps +def get_colormaps(path=config.COLORMAP_PATH): + categories = [] + maps = [] + order = {'Default': 1, 'Uniform': 2, 'Diverging': 3, 'Miscellaneous': 4} + cmap_directories = list(sorted( + os.listdir(os.path.join("static", path)), + key=lambda d: order[d] + )) + for directory in cmap_directories: + categories.append(directory) + maps_for_category = [] + for cmap in os.listdir(os.path.join("static", path, directory)): + maps_for_category.append({ + 'label': cmap[:cmap.rfind(".")], + 'src': os.path.join(os.path.join(config.COLORMAP_PATH, directory, cmap)), + }) + maps.append(maps_for_category) + return categories, maps + +class SimulationHandler(tornado.web.RequestHandler): + def get(self): + categories, colormaps = get_colormaps() + self.render('RSI.html', categories=categories, colormaps=colormaps) + +class DataConnection(tornado.websocket.WebSocketHandler): + def open(self): + logging.info("Client connected!") + self.calc = Calculation(kbins=config.TRANSFER_FUNCTION_CLIENT_SAMPLES) + # Send list of `k` values only once + logging.info("Sending k range to client"); + self.write_message(json.dumps({ + "type": "krange", + "k": self.calc.krange.tolist() + })) + + def on_close(self): + logging.info("Connection was closed") + + @gen.coroutine + def on_message(self, message): + message = json.loads(message) + param_type = message['type'] + logging.debug("Received message from client: {}".format(message)) + params = message['params'] + if param_type == "Initial": + initialDataType = str(params['initialDataType']) + + size = params["xScale"] + resolution = int(params["resolution"]) + self.calc.resolution = resolution + self.calc.size = size + + logging.info("Size: {} x {} Mpc^2, resolution: {} x {}".format(size, size, resolution, resolution)) + + SIlimit = params['SILimit'] + + if SIlimit == "None": + SIlimit = None + + sigma = float(params['sigma']) + + SI_ns = params['n_s'] + if initialDataType == "SI": + A_s = 2.214 * 10**(-9) + else: + A_s = 1 + + redshift = generate_redshifts(params["redshift"]) + self.calc.redshift = redshift + + self.write_message( + json.dumps({ + 'type': 'redshift', + 'redshift': redshift.tolist() + })) + + logging.info("Submitting initial state generation to ThreadPoolExecutor") + yield pool.submit(self.set_initial_condition, sigma, initialDataType, + SIlimit, SI_ns, A_s) + self.send_initial_state() + self.write_message(json.dumps({'type': 'success', 'sort': 'Initial'})) + + elif param_type == "Cosmo": + logging.info("Received cosmological parameters") + cosmological_parameters = params + logging.info("Submitting calculation to ThreadPoolExecutor") + messages = yield pool.submit(self.set_cosmological_parameters, cosmological_parameters) + for message in messages: + self.write_message(json.dumps(message)) + elif param_type == "Start": + logging.info("Starting propagation...") + try: + for redindex, z in enumerate(self.calc.redshift): + self.send_frame(redindex) + self.write_message(json.dumps({'type': 'success', 'sort': 'Data'})) + except Exception as e: + logging.exception(e) + self.send_exception(e) + + def send_frame(self, redindex): + # `extrema`: (minimum, maximum) of (real space) data + Valuenew, FValuenew, extrema = self.calc.getData(redindex) + logging.info("Sending data for redshift = {}".format(self.calc.redshift[redindex])) + + # Create data to be displayed in transfer function window + TransferData, _ = self.calc.getTransferData(redindex) + + self.write_message(json.dumps({'type': 'extrema', 'extrema': extrema})) + progress = float(redindex) / len(self.calc.redshift) + + real = {quantity: base64.b64encode(data.astype(np.float32)) for quantity, data in Valuenew.iteritems()} + transfer = {quantity: base64.b64encode(data.astype(np.float32)) for quantity, data in TransferData.iteritems()} + self.write_message( + json.dumps({ + 'type': 'data', + 'progress': progress, + 'real': real, + 'fourier': [], + 'transfer': transfer, + })) + + def send_initial_state(self): + Value, FValue, extrema = self.calc.getInitialData() + TransferData = np.ones(config.TRANSFER_FUNCTION_CLIENT_SAMPLES) + krange = np.zeros(config.TRANSFER_FUNCTION_CLIENT_SAMPLES) + logging.info("Sending initial data to client.") + self.write_message({ + "type": "resolution", + "value": self.calc.resolution + }) + extremastring = json.dumps({'type': 'extrema', 'extrema': extrema}) + datastring = json.dumps({ + 'type': 'data', + 'real': base64.b64encode(Value.astype(np.float32)), + 'fourier': [], + 'transfer': base64.b64encode(TransferData.astype(np.float32)), + 'k': krange.tolist() + }) + self.write_message(extremastring) + self.write_message(datastring) + + + def set_initial_condition(self, sigma, initialDataType, SIlimit, SI_ns, A_s): + try: + self.calc.setInitialConditions( + sigma=sigma, + initialDataType=initialDataType, + SIlimit=SIlimit, + SI_ns=SI_ns, + A=A_s + ) + except Exception as e: + logging.exception(e) + self.send_exception(e) + + def send_exception(self, e): + self.write_message(json.dumps({'type': 'exception', 'exception': traceback.format_exc()})) + + def set_cosmological_parameters(self, cosmologicalParameters): + try: + messages = [] + logging.info("Starting calculation...") + self.calc.setCosmologialParameters(cosmologicalParameters=cosmologicalParameters) + logging.info("Finished calculation!") + + messages.append({'type': 'success', 'sort': 'Cosmo'}) + messages.append({ + 'type': 'Cl', + 'l': self.calc.tCl.l.tolist(), + 'tCl': self.calc.tCl.tCl.tolist() + }) + messages.append({ + 'type': 'mPk', + 'kh': self.calc.mPk.kh.tolist(), + 'Pkh': self.calc.mPk.Pkh.tolist() + }) + + z_of_decoupling = self.calc.z_dec + frame_of_decoupling = np.argmin(np.abs(z_of_decoupling - self.calc.redshift)) + if self.calc.redshift[frame_of_decoupling] > z_of_decoupling: + frame_of_decoupling -= 1 + messages.append({ + 'type': 'decoupling', + 'frame': frame_of_decoupling, + 'z': z_of_decoupling}) + except Exception as e: + logging.exception(e) + self.send_exception(e) + else: + return messages + + +def main(): + logging.getLogger().setLevel(logging.DEBUG) + + application = tornado.web.Application( + [ + (r"/", SimulationHandler), + (r"/datasocket", DataConnection), + ], + template_path=os.path.join(os.path.dirname(__file__), "templates"), + static_path=os.path.join(os.path.dirname(__file__), "static"), + debug=True, + ) + + PORT = config.PORT if len(sys.argv) == 1 else int(sys.argv[1]) + application.listen(PORT) + logging.info("Application launched on http://localhost:{}".format(PORT)) + IOLoop.instance().current().start() + + +if __name__ == '__main__': + main() diff --git a/class/bbn/sBBN_2017.dat b/class/bbn/sBBN_2017.dat new file mode 100644 index 00000000..6968d4a8 --- /dev/null +++ b/class/bbn/sBBN_2017.dat @@ -0,0 +1,542 @@ +# standard BBN prediction of the primordial Helium abundance $Y_p$ as +# function of the baryon density $\omega_b h^2$ and number of extra +# radiation degrees of freedom $\Delta N = N_eff-3.046$. Impact of +# chemical potential of electron neutrinos neglected in this version. +# +# Calculated with PArthENoPE v1.2 for a neutron lifetime of 880.2 s, +# identical to standard assumptions of Planck 2017 papers. +# +# Format: +# First line must contain (num_ombh2,num_DeltaN), other lines must +# contain (ombh2,DeltaN,YHe) blank lines and lines starting with # +# neglected + +48 11 +0.00499 -3.0 0.17643 +0.00599 -3.0 0.17896 +0.00699 -3.0 0.18091 +0.00799 -3.0 0.18251 +0.00898 -3.0 0.18384 +0.00998 -3.0 0.18502 +0.01098 -3.0 0.18604 +0.01198 -3.0 0.18694 +0.01298 -3.0 0.18778 +0.01398 -3.0 0.18852 +0.01497 -3.0 0.1892 +0.01597 -3.0 0.18984 +0.01697 -3.0 0.19044 +0.01797 -3.0 0.191 +0.01897 -3.0 0.19152 +0.01997 -3.0 0.192 +0.02021 -3.0 0.19212 +0.02046 -3.0 0.19225 +0.02071 -3.0 0.19235 +0.02096 -3.0 0.19246 +0.02121 -3.0 0.19258 +0.02146 -3.0 0.19269 +0.02171 -3.0 0.1928 +0.02196 -3.0 0.19291 +0.02221 -3.0 0.19301 +0.02246 -3.0 0.19311 +0.02271 -3.0 0.19321 +0.02296 -3.0 0.19332 +0.02321 -3.0 0.19343 +0.02346 -3.0 0.19352 +0.02371 -3.0 0.19362 +0.02396 -3.0 0.19373 +0.02496 -3.0 0.1941 +0.02595 -3.0 0.19448 +0.02695 -3.0 0.19481 +0.02795 -3.0 0.19514 +0.02895 -3.0 0.19548 +0.02995 -3.0 0.19578 +0.03094 -3.0 0.19609 +0.03194 -3.0 0.19638 +0.03294 -3.0 0.19665 +0.03394 -3.0 0.19693 +0.03494 -3.0 0.19719 +0.03594 -3.0 0.19744 +0.03693 -3.0 0.19769 +0.03793 -3.0 0.19792 +0.03893 -3.0 0.19817 +0.03993 -3.0 0.19838 +0.00499 -2.0 0.19647 +0.00599 -2.0 0.1992 +0.00699 -2.0 0.20131 +0.00799 -2.0 0.203 +0.00898 -2.0 0.2044 +0.00998 -2.0 0.20562 +0.01098 -2.0 0.20669 +0.01198 -2.0 0.20763 +0.01298 -2.0 0.20848 +0.01398 -2.0 0.20923 +0.01497 -2.0 0.20995 +0.01597 -2.0 0.21061 +0.01697 -2.0 0.21122 +0.01797 -2.0 0.21177 +0.01897 -2.0 0.21229 +0.01997 -2.0 0.2128 +0.02021 -2.0 0.21292 +0.02046 -2.0 0.21304 +0.02071 -2.0 0.21316 +0.02096 -2.0 0.21328 +0.02121 -2.0 0.21339 +0.02146 -2.0 0.2135 +0.02171 -2.0 0.21361 +0.02196 -2.0 0.21373 +0.02221 -2.0 0.21382 +0.02246 -2.0 0.21392 +0.02271 -2.0 0.21403 +0.02296 -2.0 0.21412 +0.02321 -2.0 0.21424 +0.02346 -2.0 0.21433 +0.02371 -2.0 0.21444 +0.02396 -2.0 0.21455 +0.02496 -2.0 0.21491 +0.02595 -2.0 0.21528 +0.02695 -2.0 0.21564 +0.02795 -2.0 0.21598 +0.02895 -2.0 0.2163 +0.02995 -2.0 0.21662 +0.03094 -2.0 0.21692 +0.03194 -2.0 0.21722 +0.03294 -2.0 0.2175 +0.03394 -2.0 0.21776 +0.03494 -2.0 0.21804 +0.03594 -2.0 0.21828 +0.03693 -2.0 0.21855 +0.03793 -2.0 0.21878 +0.03893 -2.0 0.21902 +0.03993 -2.0 0.21923 +0.00499 -1.0 0.21295 +0.00599 -1.0 0.21585 +0.00699 -1.0 0.21807 +0.00799 -1.0 0.21983 +0.00898 -1.0 0.22131 +0.00998 -1.0 0.22255 +0.01098 -1.0 0.22365 +0.01198 -1.0 0.2246 +0.01298 -1.0 0.22548 +0.01398 -1.0 0.22626 +0.01497 -1.0 0.22696 +0.01597 -1.0 0.22764 +0.01697 -1.0 0.22826 +0.01797 -1.0 0.22882 +0.01897 -1.0 0.22934 +0.01997 -1.0 0.22984 +0.02021 -1.0 0.22998 +0.02046 -1.0 0.23009 +0.02071 -1.0 0.23022 +0.02096 -1.0 0.23033 +0.02121 -1.0 0.23043 +0.02146 -1.0 0.23056 +0.02171 -1.0 0.23068 +0.02196 -1.0 0.23078 +0.02221 -1.0 0.23089 +0.02246 -1.0 0.231 +0.02271 -1.0 0.23109 +0.02296 -1.0 0.23121 +0.02321 -1.0 0.23131 +0.02346 -1.0 0.2314 +0.02371 -1.0 0.23152 +0.02396 -1.0 0.23161 +0.02496 -1.0 0.23198 +0.02595 -1.0 0.23235 +0.02695 -1.0 0.23271 +0.02795 -1.0 0.23306 +0.02895 -1.0 0.23337 +0.02995 -1.0 0.2337 +0.03094 -1.0 0.23399 +0.03194 -1.0 0.23428 +0.03294 -1.0 0.23455 +0.03394 -1.0 0.23484 +0.03494 -1.0 0.2351 +0.03594 -1.0 0.23534 +0.03693 -1.0 0.23559 +0.03793 -1.0 0.23585 +0.03893 -1.0 0.23607 +0.03993 -1.0 0.23631 +0.00499 0.0 0.22686 +0.00599 0.0 0.22995 +0.00699 0.0 0.23226 +0.00799 0.0 0.23411 +0.00898 0.0 0.2356 +0.00998 0.0 0.23689 +0.01098 0.0 0.238 +0.01198 0.0 0.23901 +0.01298 0.0 0.23987 +0.01398 0.0 0.24066 +0.01497 0.0 0.24139 +0.01597 0.0 0.24206 +0.01697 0.0 0.24268 +0.01797 0.0 0.24324 +0.01897 0.0 0.24378 +0.01997 0.0 0.2443 +0.02021 0.0 0.24442 +0.02046 0.0 0.24454 +0.02071 0.0 0.24465 +0.02096 0.0 0.24478 +0.02121 0.0 0.24488 +0.02146 0.0 0.24498 +0.02171 0.0 0.24509 +0.02196 0.0 0.24522 +0.02221 0.0 0.24533 +0.02246 0.0 0.24543 +0.02271 0.0 0.24552 +0.02296 0.0 0.24563 +0.02321 0.0 0.24575 +0.02346 0.0 0.24585 +0.02371 0.0 0.24595 +0.02396 0.0 0.24603 +0.02496 0.0 0.24642 +0.02595 0.0 0.24679 +0.02695 0.0 0.24714 +0.02795 0.0 0.2475 +0.02895 0.0 0.24781 +0.02995 0.0 0.24812 +0.03094 0.0 0.24843 +0.03194 0.0 0.2487 +0.03294 0.0 0.24898 +0.03394 0.0 0.24926 +0.03494 0.0 0.24952 +0.03594 0.0 0.24977 +0.03693 0.0 0.25003 +0.03793 0.0 0.25027 +0.03893 0.0 0.25051 +0.03993 0.0 0.25071 +0.00499 1.0 0.23893 +0.00599 1.0 0.24216 +0.00699 1.0 0.24457 +0.00799 1.0 0.24646 +0.00898 1.0 0.24801 +0.00998 1.0 0.24932 +0.01098 1.0 0.25046 +0.01198 1.0 0.25145 +0.01298 1.0 0.25236 +0.01398 1.0 0.25315 +0.01497 1.0 0.25388 +0.01597 1.0 0.25456 +0.01697 1.0 0.25517 +0.01797 1.0 0.25577 +0.01897 1.0 0.25629 +0.01997 1.0 0.25679 +0.02021 1.0 0.25692 +0.02046 1.0 0.25704 +0.02071 1.0 0.25716 +0.02096 1.0 0.25726 +0.02121 1.0 0.25737 +0.02146 1.0 0.25749 +0.02171 1.0 0.25762 +0.02196 1.0 0.25771 +0.02221 1.0 0.25784 +0.02246 1.0 0.25794 +0.02271 1.0 0.25805 +0.02296 1.0 0.25815 +0.02321 1.0 0.25824 +0.02346 1.0 0.25836 +0.02371 1.0 0.25844 +0.02396 1.0 0.25855 +0.02496 1.0 0.25892 +0.02595 1.0 0.25928 +0.02695 1.0 0.25965 +0.02795 1.0 0.25999 +0.02895 1.0 0.26031 +0.02995 1.0 0.26062 +0.03094 1.0 0.26091 +0.03194 1.0 0.26121 +0.03294 1.0 0.26149 +0.03394 1.0 0.26176 +0.03494 1.0 0.26201 +0.03594 1.0 0.26225 +0.03693 1.0 0.26249 +0.03793 1.0 0.26273 +0.03893 1.0 0.26296 +0.03993 1.0 0.26321 +0.00499 2.0 0.2495 +0.00599 2.0 0.25288 +0.00699 2.0 0.25538 +0.00799 2.0 0.25733 +0.00898 2.0 0.25896 +0.00998 2.0 0.26028 +0.01098 2.0 0.26145 +0.01198 2.0 0.26244 +0.01298 2.0 0.26336 +0.01398 2.0 0.26417 +0.01497 2.0 0.26491 +0.01597 2.0 0.26557 +0.01697 2.0 0.26618 +0.01797 2.0 0.26678 +0.01897 2.0 0.26732 +0.01997 2.0 0.26782 +0.02021 2.0 0.26793 +0.02046 2.0 0.26806 +0.02071 2.0 0.26817 +0.02096 2.0 0.26827 +0.02121 2.0 0.26839 +0.02146 2.0 0.26852 +0.02171 2.0 0.26861 +0.02196 2.0 0.26872 +0.02221 2.0 0.26883 +0.02246 2.0 0.26896 +0.02271 2.0 0.26906 +0.02296 2.0 0.26916 +0.02321 2.0 0.26925 +0.02346 2.0 0.26935 +0.02371 2.0 0.26947 +0.02396 2.0 0.26956 +0.02496 2.0 0.26995 +0.02595 2.0 0.27032 +0.02695 2.0 0.27065 +0.02795 2.0 0.271 +0.02895 2.0 0.27131 +0.02995 2.0 0.27161 +0.03094 2.0 0.27191 +0.03194 2.0 0.27219 +0.03294 2.0 0.27249 +0.03394 2.0 0.27275 +0.03494 2.0 0.27301 +0.03594 2.0 0.27326 +0.03693 2.0 0.27351 +0.03793 2.0 0.27372 +0.03893 2.0 0.27397 +0.03993 2.0 0.27418 +0.00499 3.0 0.25893 +0.00599 3.0 0.26246 +0.00699 3.0 0.26505 +0.00799 3.0 0.26705 +0.00898 3.0 0.2687 +0.00998 3.0 0.27007 +0.01098 3.0 0.27122 +0.01198 3.0 0.27227 +0.01298 3.0 0.27318 +0.01398 3.0 0.27398 +0.01497 3.0 0.27471 +0.01597 3.0 0.27541 +0.01697 3.0 0.27604 +0.01797 3.0 0.2766 +0.01897 3.0 0.27716 +0.01997 3.0 0.27765 +0.02021 3.0 0.27776 +0.02046 3.0 0.2779 +0.02071 3.0 0.27801 +0.02096 3.0 0.27813 +0.02121 3.0 0.27824 +0.02146 3.0 0.27836 +0.02171 3.0 0.27845 +0.02196 3.0 0.27857 +0.02221 3.0 0.27868 +0.02246 3.0 0.27877 +0.02271 3.0 0.27888 +0.02296 3.0 0.27898 +0.02321 3.0 0.27908 +0.02346 3.0 0.2792 +0.02371 3.0 0.27929 +0.02396 3.0 0.2794 +0.02496 3.0 0.27978 +0.02595 3.0 0.28014 +0.02695 3.0 0.28049 +0.02795 3.0 0.2808 +0.02895 3.0 0.28114 +0.02995 3.0 0.28145 +0.03094 3.0 0.28172 +0.03194 3.0 0.28203 +0.03294 3.0 0.2823 +0.03394 3.0 0.28255 +0.03494 3.0 0.28282 +0.03594 3.0 0.28305 +0.03693 3.0 0.28332 +0.03793 3.0 0.28353 +0.03893 3.0 0.28377 +0.03993 3.0 0.28399 +0.00499 4.0 0.2674 +0.00599 4.0 0.27107 +0.00699 4.0 0.27376 +0.00799 4.0 0.27583 +0.00898 4.0 0.2775 +0.00998 4.0 0.2789 +0.01098 4.0 0.28007 +0.01198 4.0 0.2811 +0.01298 4.0 0.28202 +0.01398 4.0 0.28285 +0.01497 4.0 0.2836 +0.01597 4.0 0.28427 +0.01697 4.0 0.28489 +0.01797 4.0 0.28547 +0.01897 4.0 0.28602 +0.01997 4.0 0.28654 +0.02021 4.0 0.28664 +0.02046 4.0 0.28676 +0.02071 4.0 0.28687 +0.02096 4.0 0.287 +0.02121 4.0 0.2871 +0.02146 4.0 0.28723 +0.02171 4.0 0.28732 +0.02196 4.0 0.28744 +0.02221 4.0 0.28755 +0.02246 4.0 0.28765 +0.02271 4.0 0.28777 +0.02296 4.0 0.28785 +0.02321 4.0 0.28797 +0.02346 4.0 0.28806 +0.02371 4.0 0.28817 +0.02396 4.0 0.28827 +0.02496 4.0 0.28863 +0.02595 4.0 0.289 +0.02695 4.0 0.28936 +0.02795 4.0 0.28967 +0.02895 4.0 0.28999 +0.02995 4.0 0.2903 +0.03094 4.0 0.2906 +0.03194 4.0 0.29088 +0.03294 4.0 0.29113 +0.03394 4.0 0.29142 +0.03494 4.0 0.29167 +0.03594 4.0 0.2919 +0.03693 4.0 0.29216 +0.03793 4.0 0.29237 +0.03893 4.0 0.29259 +0.03993 4.0 0.29281 +0.00499 5.0 0.27505 +0.00599 5.0 0.27891 +0.00699 5.0 0.28166 +0.00799 5.0 0.28378 +0.00898 5.0 0.2855 +0.00998 5.0 0.2869 +0.01098 5.0 0.28814 +0.01198 5.0 0.28917 +0.01298 5.0 0.29011 +0.01398 5.0 0.29092 +0.01497 5.0 0.29169 +0.01597 5.0 0.29235 +0.01697 5.0 0.293 +0.01797 5.0 0.29356 +0.01897 5.0 0.29411 +0.01997 5.0 0.29461 +0.02021 5.0 0.29472 +0.02046 5.0 0.29484 +0.02071 5.0 0.29497 +0.02096 5.0 0.29507 +0.02121 5.0 0.29519 +0.02146 5.0 0.29532 +0.02171 5.0 0.29543 +0.02196 5.0 0.29552 +0.02221 5.0 0.29564 +0.02246 5.0 0.29573 +0.02271 5.0 0.29585 +0.02296 5.0 0.29594 +0.02321 5.0 0.29605 +0.02346 5.0 0.29616 +0.02371 5.0 0.29624 +0.02396 5.0 0.29635 +0.02496 5.0 0.29671 +0.02595 5.0 0.29708 +0.02695 5.0 0.29743 +0.02795 5.0 0.29774 +0.02895 5.0 0.29807 +0.02995 5.0 0.29836 +0.03094 5.0 0.29865 +0.03194 5.0 0.29893 +0.03294 5.0 0.2992 +0.03394 5.0 0.29946 +0.03494 5.0 0.29974 +0.03594 5.0 0.29996 +0.03693 5.0 0.30022 +0.03793 5.0 0.30042 +0.03893 5.0 0.30064 +0.03993 5.0 0.30087 +0.00499 6.0 0.28209 +0.00599 6.0 0.28606 +0.00699 6.0 0.28893 +0.00799 6.0 0.2911 +0.00898 6.0 0.29285 +0.00998 6.0 0.29427 +0.01098 6.0 0.2955 +0.01198 6.0 0.29658 +0.01298 6.0 0.29749 +0.01398 6.0 0.29834 +0.01497 6.0 0.29908 +0.01597 6.0 0.29978 +0.01697 6.0 0.30041 +0.01797 6.0 0.30099 +0.01897 6.0 0.30153 +0.01997 6.0 0.30203 +0.02021 6.0 0.30213 +0.02046 6.0 0.30225 +0.02071 6.0 0.30237 +0.02096 6.0 0.30251 +0.02121 6.0 0.30262 +0.02146 6.0 0.30271 +0.02171 6.0 0.30284 +0.02196 6.0 0.30295 +0.02221 6.0 0.30305 +0.02246 6.0 0.30316 +0.02271 6.0 0.30325 +0.02296 6.0 0.30336 +0.02321 6.0 0.30347 +0.02346 6.0 0.30357 +0.02371 6.0 0.30365 +0.02396 6.0 0.30374 +0.02496 6.0 0.30411 +0.02595 6.0 0.30449 +0.02695 6.0 0.30483 +0.02795 6.0 0.30516 +0.02895 6.0 0.30546 +0.02995 6.0 0.30576 +0.03094 6.0 0.30606 +0.03194 6.0 0.30632 +0.03294 6.0 0.30659 +0.03394 6.0 0.30686 +0.03494 6.0 0.30712 +0.03594 6.0 0.30736 +0.03693 6.0 0.30759 +0.03793 6.0 0.3078 +0.03893 6.0 0.30802 +0.03993 6.0 0.30823 +0.00499 7.0 0.28851 +0.00599 7.0 0.29265 +0.00699 7.0 0.29559 +0.00799 7.0 0.29784 +0.00898 7.0 0.29963 +0.00998 7.0 0.30107 +0.01098 7.0 0.30231 +0.01198 7.0 0.30341 +0.01298 7.0 0.30432 +0.01398 7.0 0.30518 +0.01497 7.0 0.30592 +0.01597 7.0 0.30663 +0.01697 7.0 0.30726 +0.01797 7.0 0.30783 +0.01897 7.0 0.30835 +0.01997 7.0 0.30888 +0.02021 7.0 0.309 +0.02046 7.0 0.30911 +0.02071 7.0 0.30923 +0.02096 7.0 0.30935 +0.02121 7.0 0.30946 +0.02146 7.0 0.30957 +0.02171 7.0 0.30966 +0.02196 7.0 0.30979 +0.02221 7.0 0.30988 +0.02246 7.0 0.30998 +0.02271 7.0 0.3101 +0.02296 7.0 0.31021 +0.02321 7.0 0.31031 +0.02346 7.0 0.31041 +0.02371 7.0 0.31049 +0.02396 7.0 0.31058 +0.02496 7.0 0.31098 +0.02595 7.0 0.31131 +0.02695 7.0 0.31168 +0.02795 7.0 0.31198 +0.02895 7.0 0.31229 +0.02995 7.0 0.31259 +0.03094 7.0 0.31289 +0.03194 7.0 0.31317 +0.03294 7.0 0.31343 +0.03394 7.0 0.31369 +0.03494 7.0 0.31392 +0.03594 7.0 0.31418 +0.03693 7.0 0.3144 +0.03793 7.0 0.31462 +0.03893 7.0 0.31484 +0.03993 7.0 0.31506 diff --git a/class/bbn/sBBN_2017_marcucci.dat b/class/bbn/sBBN_2017_marcucci.dat new file mode 100644 index 00000000..25f7ed8a --- /dev/null +++ b/class/bbn/sBBN_2017_marcucci.dat @@ -0,0 +1,543 @@ +# standard BBN prediction of the primordial Helium abundance $Y_p$ as +# function of the baryon density $\omega_b h^2$ and number of extra +# radiation degrees of freedom $\Delta N = N_eff-3.046$. Impact of +# chemical potential of electron neutrinos neglected in this version. +# +# Calculated with PArthENoPE v1.2 for a neutron lifetime of 880.2 s, +# and with the rate d(p,gamma)^3He coming from ab initio calculations +# by Marcucci et al. 2015. +# +# Format: +# First line must contain (num_ombh2,num_DeltaN), other lines must +# contain (ombh2,DeltaN,YHe) blank lines and lines starting with # +# neglected + +48 11 +0.00499 -3.0 0.17644 +0.00599 -3.0 0.17896 +0.00699 -3.0 0.18092 +0.00799 -3.0 0.18252 +0.00898 -3.0 0.18387 +0.00998 -3.0 0.18503 +0.01098 -3.0 0.18603 +0.01198 -3.0 0.18696 +0.01298 -3.0 0.18778 +0.01398 -3.0 0.18852 +0.01497 -3.0 0.18922 +0.01597 -3.0 0.18985 +0.01697 -3.0 0.19045 +0.01797 -3.0 0.191 +0.01897 -3.0 0.19152 +0.01997 -3.0 0.19202 +0.02021 -3.0 0.19214 +0.02046 -3.0 0.19226 +0.02071 -3.0 0.19236 +0.02096 -3.0 0.19248 +0.02121 -3.0 0.1926 +0.02146 -3.0 0.19271 +0.02171 -3.0 0.19281 +0.02196 -3.0 0.19292 +0.02221 -3.0 0.19301 +0.02246 -3.0 0.19313 +0.02271 -3.0 0.19323 +0.02296 -3.0 0.19334 +0.02321 -3.0 0.19343 +0.02346 -3.0 0.19354 +0.02371 -3.0 0.19363 +0.02396 -3.0 0.19372 +0.02496 -3.0 0.19411 +0.02595 -3.0 0.19449 +0.02695 -3.0 0.19482 +0.02795 -3.0 0.19517 +0.02895 -3.0 0.19549 +0.02995 -3.0 0.19579 +0.03094 -3.0 0.1961 +0.03194 -3.0 0.19638 +0.03294 -3.0 0.19667 +0.03394 -3.0 0.19695 +0.03494 -3.0 0.19721 +0.03594 -3.0 0.19746 +0.03693 -3.0 0.19771 +0.03793 -3.0 0.19793 +0.03893 -3.0 0.19819 +0.03993 -3.0 0.19841 +0.00499 -2.0 0.1965 +0.00599 -2.0 0.19921 +0.00699 -2.0 0.20132 +0.00799 -2.0 0.20299 +0.00898 -2.0 0.2044 +0.00998 -2.0 0.20563 +0.01098 -2.0 0.20669 +0.01198 -2.0 0.20764 +0.01298 -2.0 0.20849 +0.01398 -2.0 0.20925 +0.01497 -2.0 0.20996 +0.01597 -2.0 0.21061 +0.01697 -2.0 0.21123 +0.01797 -2.0 0.21177 +0.01897 -2.0 0.2123 +0.01997 -2.0 0.21281 +0.02021 -2.0 0.21292 +0.02046 -2.0 0.21305 +0.02071 -2.0 0.21316 +0.02096 -2.0 0.21328 +0.02121 -2.0 0.2134 +0.02146 -2.0 0.2135 +0.02171 -2.0 0.21361 +0.02196 -2.0 0.21372 +0.02221 -2.0 0.21384 +0.02246 -2.0 0.21395 +0.02271 -2.0 0.21403 +0.02296 -2.0 0.21414 +0.02321 -2.0 0.21424 +0.02346 -2.0 0.21435 +0.02371 -2.0 0.21445 +0.02396 -2.0 0.21455 +0.02496 -2.0 0.21493 +0.02595 -2.0 0.21531 +0.02695 -2.0 0.21566 +0.02795 -2.0 0.216 +0.02895 -2.0 0.21634 +0.02995 -2.0 0.21663 +0.03094 -2.0 0.21694 +0.03194 -2.0 0.21721 +0.03294 -2.0 0.21751 +0.03394 -2.0 0.21778 +0.03494 -2.0 0.21805 +0.03594 -2.0 0.21831 +0.03693 -2.0 0.21856 +0.03793 -2.0 0.2188 +0.03893 -2.0 0.21902 +0.03993 -2.0 0.21926 +0.00499 -1.0 0.21295 +0.00599 -1.0 0.21586 +0.00699 -1.0 0.21808 +0.00799 -1.0 0.21983 +0.00898 -1.0 0.22132 +0.00998 -1.0 0.22256 +0.01098 -1.0 0.22365 +0.01198 -1.0 0.22462 +0.01298 -1.0 0.22547 +0.01398 -1.0 0.22628 +0.01497 -1.0 0.22697 +0.01597 -1.0 0.22764 +0.01697 -1.0 0.22827 +0.01797 -1.0 0.22884 +0.01897 -1.0 0.22935 +0.01997 -1.0 0.22987 +0.02021 -1.0 0.22999 +0.02046 -1.0 0.23009 +0.02071 -1.0 0.23021 +0.02096 -1.0 0.23035 +0.02121 -1.0 0.23046 +0.02146 -1.0 0.23057 +0.02171 -1.0 0.23068 +0.02196 -1.0 0.23078 +0.02221 -1.0 0.2309 +0.02246 -1.0 0.23099 +0.02271 -1.0 0.2311 +0.02296 -1.0 0.23122 +0.02321 -1.0 0.23131 +0.02346 -1.0 0.23143 +0.02371 -1.0 0.23153 +0.02396 -1.0 0.23161 +0.02496 -1.0 0.23199 +0.02595 -1.0 0.23237 +0.02695 -1.0 0.23273 +0.02795 -1.0 0.23307 +0.02895 -1.0 0.23339 +0.02995 -1.0 0.23369 +0.03094 -1.0 0.234 +0.03194 -1.0 0.23429 +0.03294 -1.0 0.23458 +0.03394 -1.0 0.23485 +0.03494 -1.0 0.2351 +0.03594 -1.0 0.23536 +0.03693 -1.0 0.23562 +0.03793 -1.0 0.23587 +0.03893 -1.0 0.23608 +0.03993 -1.0 0.23633 +0.00499 0.0 0.22688 +0.00599 0.0 0.22997 +0.00699 0.0 0.23227 +0.00799 0.0 0.2341 +0.00898 0.0 0.23562 +0.00998 0.0 0.23691 +0.01098 0.0 0.23802 +0.01198 0.0 0.239 +0.01298 0.0 0.23988 +0.01398 0.0 0.24067 +0.01497 0.0 0.24141 +0.01597 0.0 0.24207 +0.01697 0.0 0.24267 +0.01797 0.0 0.24327 +0.01897 0.0 0.24379 +0.01997 0.0 0.24431 +0.02021 0.0 0.24442 +0.02046 0.0 0.24453 +0.02071 0.0 0.24467 +0.02096 0.0 0.24478 +0.02121 0.0 0.2449 +0.02146 0.0 0.24499 +0.02171 0.0 0.2451 +0.02196 0.0 0.24521 +0.02221 0.0 0.24532 +0.02246 0.0 0.24544 +0.02271 0.0 0.24553 +0.02296 0.0 0.24565 +0.02321 0.0 0.24575 +0.02346 0.0 0.24584 +0.02371 0.0 0.24594 +0.02396 0.0 0.24604 +0.02496 0.0 0.24644 +0.02595 0.0 0.24681 +0.02695 0.0 0.24717 +0.02795 0.0 0.24749 +0.02895 0.0 0.24781 +0.02995 0.0 0.24814 +0.03094 0.0 0.24844 +0.03194 0.0 0.24871 +0.03294 0.0 0.24901 +0.03394 0.0 0.24928 +0.03494 0.0 0.24953 +0.03594 0.0 0.2498 +0.03693 0.0 0.25004 +0.03793 0.0 0.25027 +0.03893 0.0 0.25051 +0.03993 0.0 0.25074 +0.00499 1.0 0.23892 +0.00599 1.0 0.24217 +0.00699 1.0 0.24456 +0.00799 1.0 0.24647 +0.00898 1.0 0.24801 +0.00998 1.0 0.24933 +0.01098 1.0 0.25048 +0.01198 1.0 0.25147 +0.01298 1.0 0.25235 +0.01398 1.0 0.25318 +0.01497 1.0 0.25389 +0.01597 1.0 0.25457 +0.01697 1.0 0.2552 +0.01797 1.0 0.25578 +0.01897 1.0 0.25629 +0.01997 1.0 0.25679 +0.02021 1.0 0.25693 +0.02046 1.0 0.25703 +0.02071 1.0 0.25717 +0.02096 1.0 0.25727 +0.02121 1.0 0.25738 +0.02146 1.0 0.2575 +0.02171 1.0 0.25762 +0.02196 1.0 0.25773 +0.02221 1.0 0.25783 +0.02246 1.0 0.25794 +0.02271 1.0 0.25804 +0.02296 1.0 0.25815 +0.02321 1.0 0.25827 +0.02346 1.0 0.25837 +0.02371 1.0 0.25846 +0.02396 1.0 0.25855 +0.02496 1.0 0.25895 +0.02595 1.0 0.25929 +0.02695 1.0 0.25967 +0.02795 1.0 0.26 +0.02895 1.0 0.26032 +0.02995 1.0 0.26062 +0.03094 1.0 0.26093 +0.03194 1.0 0.26122 +0.03294 1.0 0.2615 +0.03394 1.0 0.26175 +0.03494 1.0 0.26202 +0.03594 1.0 0.26227 +0.03693 1.0 0.26252 +0.03793 1.0 0.26274 +0.03893 1.0 0.26299 +0.03993 1.0 0.2632 +0.00499 2.0 0.24951 +0.00599 2.0 0.25289 +0.00699 2.0 0.2554 +0.00799 2.0 0.25736 +0.00898 2.0 0.25894 +0.00998 2.0 0.26029 +0.01098 2.0 0.26144 +0.01198 2.0 0.26244 +0.01298 2.0 0.26336 +0.01398 2.0 0.26418 +0.01497 2.0 0.2649 +0.01597 2.0 0.26557 +0.01697 2.0 0.26619 +0.01797 2.0 0.26679 +0.01897 2.0 0.26731 +0.01997 2.0 0.26782 +0.02021 2.0 0.26795 +0.02046 2.0 0.26807 +0.02071 2.0 0.26816 +0.02096 2.0 0.2683 +0.02121 2.0 0.26839 +0.02146 2.0 0.26852 +0.02171 2.0 0.26864 +0.02196 2.0 0.26875 +0.02221 2.0 0.26884 +0.02246 2.0 0.26894 +0.02271 2.0 0.26905 +0.02296 2.0 0.26918 +0.02321 2.0 0.26927 +0.02346 2.0 0.26938 +0.02371 2.0 0.26946 +0.02396 2.0 0.26956 +0.02496 2.0 0.26996 +0.02595 2.0 0.27031 +0.02695 2.0 0.27067 +0.02795 2.0 0.27101 +0.02895 2.0 0.27132 +0.02995 2.0 0.27161 +0.03094 2.0 0.27191 +0.03194 2.0 0.27222 +0.03294 2.0 0.27248 +0.03394 2.0 0.27276 +0.03494 2.0 0.27303 +0.03594 2.0 0.27327 +0.03693 2.0 0.27351 +0.03793 2.0 0.27375 +0.03893 2.0 0.27398 +0.03993 2.0 0.27419 +0.00499 3.0 0.25892 +0.00599 3.0 0.26245 +0.00699 3.0 0.26504 +0.00799 3.0 0.26706 +0.00898 3.0 0.26871 +0.00998 3.0 0.27008 +0.01098 3.0 0.27123 +0.01198 3.0 0.27226 +0.01298 3.0 0.27319 +0.01398 3.0 0.27399 +0.01497 3.0 0.27472 +0.01597 3.0 0.2754 +0.01697 3.0 0.27605 +0.01797 3.0 0.27663 +0.01897 3.0 0.27716 +0.01997 3.0 0.27764 +0.02021 3.0 0.27777 +0.02046 3.0 0.2779 +0.02071 3.0 0.278 +0.02096 3.0 0.27812 +0.02121 3.0 0.27825 +0.02146 3.0 0.27836 +0.02171 3.0 0.27846 +0.02196 3.0 0.27857 +0.02221 3.0 0.27867 +0.02246 3.0 0.27878 +0.02271 3.0 0.2789 +0.02296 3.0 0.27901 +0.02321 3.0 0.27911 +0.02346 3.0 0.27919 +0.02371 3.0 0.27931 +0.02396 3.0 0.27941 +0.02496 3.0 0.27977 +0.02595 3.0 0.28014 +0.02695 3.0 0.28049 +0.02795 3.0 0.28083 +0.02895 3.0 0.28113 +0.02995 3.0 0.28145 +0.03094 3.0 0.28175 +0.03194 3.0 0.28204 +0.03294 3.0 0.28229 +0.03394 3.0 0.28258 +0.03494 3.0 0.28283 +0.03594 3.0 0.28308 +0.03693 3.0 0.2833 +0.03793 3.0 0.28354 +0.03893 3.0 0.28377 +0.03993 3.0 0.28398 +0.00499 4.0 0.2674 +0.00599 4.0 0.27106 +0.00699 4.0 0.27376 +0.00799 4.0 0.27582 +0.00898 4.0 0.27751 +0.00998 4.0 0.2789 +0.01098 4.0 0.28009 +0.01198 4.0 0.28111 +0.01298 4.0 0.28203 +0.01398 4.0 0.28287 +0.01497 4.0 0.28361 +0.01597 4.0 0.28427 +0.01697 4.0 0.2849 +0.01797 4.0 0.2855 +0.01897 4.0 0.28602 +0.01997 4.0 0.28654 +0.02021 4.0 0.28665 +0.02046 4.0 0.28678 +0.02071 4.0 0.28689 +0.02096 4.0 0.28699 +0.02121 4.0 0.2871 +0.02146 4.0 0.28724 +0.02171 4.0 0.28735 +0.02196 4.0 0.28745 +0.02221 4.0 0.28756 +0.02246 4.0 0.28767 +0.02271 4.0 0.28775 +0.02296 4.0 0.28788 +0.02321 4.0 0.28796 +0.02346 4.0 0.28808 +0.02371 4.0 0.28816 +0.02396 4.0 0.28829 +0.02496 4.0 0.28864 +0.02595 4.0 0.289 +0.02695 4.0 0.28936 +0.02795 4.0 0.28968 +0.02895 4.0 0.29002 +0.02995 4.0 0.2903 +0.03094 4.0 0.29059 +0.03194 4.0 0.29087 +0.03294 4.0 0.29116 +0.03394 4.0 0.29141 +0.03494 4.0 0.29168 +0.03594 4.0 0.29193 +0.03693 4.0 0.29215 +0.03793 4.0 0.29238 +0.03893 4.0 0.29262 +0.03993 4.0 0.29282 +0.00499 5.0 0.27508 +0.00599 5.0 0.2789 +0.00699 5.0 0.28168 +0.00799 5.0 0.28379 +0.00898 5.0 0.2855 +0.00998 5.0 0.28693 +0.01098 5.0 0.28812 +0.01198 5.0 0.28919 +0.01298 5.0 0.2901 +0.01398 5.0 0.29093 +0.01497 5.0 0.29167 +0.01597 5.0 0.29236 +0.01697 5.0 0.29299 +0.01797 5.0 0.29356 +0.01897 5.0 0.2941 +0.01997 5.0 0.2946 +0.02021 5.0 0.29474 +0.02046 5.0 0.29484 +0.02071 5.0 0.29496 +0.02096 5.0 0.29508 +0.02121 5.0 0.29519 +0.02146 5.0 0.2953 +0.02171 5.0 0.29543 +0.02196 5.0 0.29554 +0.02221 5.0 0.29565 +0.02246 5.0 0.29576 +0.02271 5.0 0.29586 +0.02296 5.0 0.29594 +0.02321 5.0 0.29606 +0.02346 5.0 0.29614 +0.02371 5.0 0.29625 +0.02396 5.0 0.29636 +0.02496 5.0 0.29673 +0.02595 5.0 0.29709 +0.02695 5.0 0.29742 +0.02795 5.0 0.29776 +0.02895 5.0 0.29806 +0.02995 5.0 0.29836 +0.03094 5.0 0.29866 +0.03194 5.0 0.29895 +0.03294 5.0 0.29921 +0.03394 5.0 0.29949 +0.03494 5.0 0.29972 +0.03594 5.0 0.29997 +0.03693 5.0 0.3002 +0.03793 5.0 0.30044 +0.03893 5.0 0.30065 +0.03993 5.0 0.30089 +0.00499 6.0 0.28208 +0.00599 6.0 0.28607 +0.00699 6.0 0.28892 +0.00799 6.0 0.29111 +0.00898 6.0 0.29284 +0.00998 6.0 0.2943 +0.01098 6.0 0.29552 +0.01198 6.0 0.29658 +0.01298 6.0 0.2975 +0.01398 6.0 0.29835 +0.01497 6.0 0.29909 +0.01597 6.0 0.29979 +0.01697 6.0 0.30041 +0.01797 6.0 0.30099 +0.01897 6.0 0.30152 +0.01997 6.0 0.30204 +0.02021 6.0 0.30214 +0.02046 6.0 0.30226 +0.02071 6.0 0.30239 +0.02096 6.0 0.30249 +0.02121 6.0 0.30261 +0.02146 6.0 0.30273 +0.02171 6.0 0.30284 +0.02196 6.0 0.30294 +0.02221 6.0 0.30306 +0.02246 6.0 0.30317 +0.02271 6.0 0.30327 +0.02296 6.0 0.30338 +0.02321 6.0 0.30346 +0.02346 6.0 0.30357 +0.02371 6.0 0.30368 +0.02396 6.0 0.30378 +0.02496 6.0 0.30412 +0.02595 6.0 0.30449 +0.02695 6.0 0.30484 +0.02795 6.0 0.30515 +0.02895 6.0 0.30549 +0.02995 6.0 0.30576 +0.03094 6.0 0.30605 +0.03194 6.0 0.30635 +0.03294 6.0 0.3066 +0.03394 6.0 0.30688 +0.03494 6.0 0.30711 +0.03594 6.0 0.30737 +0.03693 6.0 0.30759 +0.03793 6.0 0.30783 +0.03893 6.0 0.30803 +0.03993 6.0 0.30824 +0.00499 7.0 0.28853 +0.00599 7.0 0.29268 +0.00699 7.0 0.29562 +0.00799 7.0 0.29783 +0.00898 7.0 0.29963 +0.00998 7.0 0.30109 +0.01098 7.0 0.30232 +0.01198 7.0 0.30341 +0.01298 7.0 0.30433 +0.01398 7.0 0.30517 +0.01497 7.0 0.30594 +0.01597 7.0 0.30664 +0.01697 7.0 0.30725 +0.01797 7.0 0.30782 +0.01897 7.0 0.30836 +0.01997 7.0 0.30886 +0.02021 7.0 0.309 +0.02046 7.0 0.3091 +0.02071 7.0 0.30922 +0.02096 7.0 0.30936 +0.02121 7.0 0.30947 +0.02146 7.0 0.30956 +0.02171 7.0 0.30967 +0.02196 7.0 0.30979 +0.02221 7.0 0.30988 +0.02246 7.0 0.30999 +0.02271 7.0 0.31009 +0.02296 7.0 0.3102 +0.02321 7.0 0.3103 +0.02346 7.0 0.31042 +0.02371 7.0 0.3105 +0.02396 7.0 0.31061 +0.02496 7.0 0.31097 +0.02595 7.0 0.31133 +0.02695 7.0 0.31167 +0.02795 7.0 0.31199 +0.02895 7.0 0.3123 +0.02995 7.0 0.31259 +0.03094 7.0 0.31288 +0.03194 7.0 0.31318 +0.03294 7.0 0.31345 +0.03394 7.0 0.3137 +0.03494 7.0 0.31393 +0.03594 7.0 0.31417 +0.03693 7.0 0.31441 +0.03793 7.0 0.31463 +0.03893 7.0 0.31485 +0.03993 7.0 0.31505 diff --git a/class/cl_permille.pre b/class/cl_permille.pre new file mode 100644 index 00000000..270cd014 --- /dev/null +++ b/class/cl_permille.pre @@ -0,0 +1,7 @@ +# precision file to be passed as input in order to achieve at least percent precision on scalar Cls +hyper_flat_approximation_nu = 7000. +transfer_neglect_delta_k_S_t0 = 0.17 +transfer_neglect_delta_k_S_t1 = 0.05 +transfer_neglect_delta_k_S_t2 = 0.17 +transfer_neglect_delta_k_S_e = 0.13 +delta_l_max=1000 diff --git a/class/cl_ref.pre b/class/cl_ref.pre new file mode 100644 index 00000000..376e5bbb --- /dev/null +++ b/class/cl_ref.pre @@ -0,0 +1,82 @@ +# this file achieves maximum precision for the CMB: each ClTT and ClEE, lensed and unlensed, are stable at the 0.01% level + +tol_ncdm_bg = 1.e-10 + +recfast_Nz0=100000 +tol_thermo_integration=1.e-5 + +recfast_x_He0_trigger_delta = 0.01 +recfast_x_H0_trigger_delta = 0.01 + +evolver=0 + +k_min_tau0=0.002 +k_max_tau0_over_l_max=3. +k_step_sub=0.015 +k_step_super=0.0001 +k_step_super_reduction=0.1 + +start_small_k_at_tau_c_over_tau_h = 0.0004 +start_large_k_at_tau_h_over_tau_k = 0.05 +tight_coupling_trigger_tau_c_over_tau_h=0.005 +tight_coupling_trigger_tau_c_over_tau_k=0.008 +start_sources_at_tau_c_over_tau_h = 0.006 + +l_max_g=50 +l_max_pol_g=25 +l_max_ur=50 +l_max_ncdm=50 + +tol_perturb_integration=1.e-6 +perturb_sampling_stepsize=0.01 + +radiation_streaming_approximation = 2 +radiation_streaming_trigger_tau_over_tau_k = 240. +radiation_streaming_trigger_tau_c_over_tau = 100. + +ur_fluid_approximation = 2 +ur_fluid_trigger_tau_over_tau_k = 50. + +ncdm_fluid_approximation = 3 +ncdm_fluid_trigger_tau_over_tau_k = 51. + +tol_ncdm_synchronous = 1.e-10 +tol_ncdm_newtonian = 1.e-10 + +l_logstep=1.026 +l_linstep=25 + +hyper_sampling_flat = 12. +hyper_sampling_curved_low_nu = 10. +hyper_sampling_curved_high_nu = 10. +hyper_nu_sampling_step = 10. +hyper_phi_min_abs = 1.e-10 +hyper_x_tol = 1.e-4 +hyper_flat_approximation_nu = 1.e6 + +q_linstep=0.20 +q_logstep_spline= 20. +q_logstep_trapzd = 0.5 +q_numstep_transition = 250 + +transfer_neglect_delta_k_S_t0 = 100. +transfer_neglect_delta_k_S_t1 = 100. +transfer_neglect_delta_k_S_t2 = 100. +transfer_neglect_delta_k_S_e = 100. +transfer_neglect_delta_k_V_t1 = 100. +transfer_neglect_delta_k_V_t2 = 100. +transfer_neglect_delta_k_V_e = 100. +transfer_neglect_delta_k_V_b = 100. +transfer_neglect_delta_k_T_t2 = 100. +transfer_neglect_delta_k_T_e = 100. +transfer_neglect_delta_k_T_b = 100. + +neglect_CMB_sources_below_visibility = 1.e-30 +transfer_neglect_late_source = 3000. + +halofit_k_per_decade = 3000. + +l_switch_limber = 40. +accurate_lensing=1 +num_mu_minus_lmax = 1000. +delta_l_max = 1000. \ No newline at end of file diff --git a/class/cpp/ClassEngine.cc b/class/cpp/ClassEngine.cc new file mode 100644 index 00000000..7c476e87 --- /dev/null +++ b/class/cpp/ClassEngine.cc @@ -0,0 +1,721 @@ +//-------------------------------------------------------------------------- +// +// Description: +// class ClassEngine : see header file (ClassEngine.hh) for description. +// +//------------------------------------------------------------------------ +//----------------------- +// This Class's Header -- +//----------------------- +#include "ClassEngine.hh" +// ------------------------ +// Collaborating classes -- +//------------------------- +// C++ +//-------------------- +#include +#include +#include +#include +#include +#include +#include +#include + +//#define DBUG + +using namespace std; + +template std::string str(const T &x){ + std::ostringstream os; + os << x; + return os.str(); +} +//specilization +template<> std::string str (const float &x){ + std::ostringstream os; + os << setprecision(8) << x; + return os.str(); +} +template<> std::string str (const double &x){ + std::ostringstream os; + os << setprecision(16) << x; + return os.str(); +} +template<> std::string str (const bool &x){ + { return x ? "yes" : "no"; } +} + +template<> std::string str (const std::string &x) {return x;} + +std::string str (const char* s){return string(s);} + +//instanciations +template string str(const int &x); +template string str(const signed char &x); +template string str(const unsigned char &x); +template string str(const short &x); +template string str(const unsigned short &x); +template string str(const unsigned int &x); +template string str(const long &x); +template string str(const unsigned long &x); +template string str(const long long &x); +template string str(const unsigned long long &x); + +//--------------- +// Constructors -- +//---------------- +ClassEngine::ClassEngine(const ClassParams& pars, bool verbose): cl(0),dofree(true){ + + //prepare fp structure + size_t n=pars.size(); + // + parser_init(&fc,n,"pipo",_errmsg); + + //config + for (size_t i=0;i> _lmax; + } + } + if( verbose ) cout << __FILE__ << " : using lmax=" << _lmax <0); // this collides with transfer function calculations + + //input + if (input_init(&fc,&pr,&ba,&th,&pt,&tr,&pm,&sp,&nl,&le,&op,_errmsg) == _FAILURE_) + throw invalid_argument(_errmsg); + + //proetction parametres mal defini + for (size_t i=0;i(precision_file.c_str()),&fc_precision,_errmsg) == _FAILURE_){ + throw invalid_argument(_errmsg); + } + + //pars + struct file_content fc_input; + fc_input.size = 0; + fc_input.filename=new char[1]; + //prepare fc par structure + size_t n=pars.size(); + parser_init(&fc_input,n,"pipo",_errmsg); + //config + for (size_t i=0;i> _lmax; + } + } + if( verbose ) cout << __FILE__ << " : using lmax=" << _lmax <0); + + + + //concatenate both + if (parser_cat(&fc_input,&fc_precision,&fc,_errmsg) == _FAILURE_) throw invalid_argument(_errmsg); + + //parser_free(&fc_input); + parser_free(&fc_precision); + + //input + if (input_init(&fc,&pr,&ba,&th,&pt,&tr,&pm,&sp,&nl,&le,&op,_errmsg) == _FAILURE_) + throw invalid_argument(_errmsg); + + //proetction parametres mal defini + for (size_t i=0;i& par){ + dofree && freeStructs(); + for (size_t i=0;i%s\n",errmsg); + dofree=false; + return _FAILURE_; + } + + if (background_init(ppr,pba) == _FAILURE_) { + printf("\n\nError running background_init \n=>%s\n",pba->error_message); + dofree=false; + return _FAILURE_; + } + + if (thermodynamics_init(ppr,pba,pth) == _FAILURE_) { + printf("\n\nError in thermodynamics_init \n=>%s\n",pth->error_message); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + if (perturb_init(ppr,pba,pth,ppt) == _FAILURE_) { + printf("\n\nError in perturb_init \n=>%s\n",ppt->error_message); + thermodynamics_free(&th); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + if (primordial_init(ppr,ppt,ppm) == _FAILURE_) { + printf("\n\nError in primordial_init \n=>%s\n",ppm->error_message); + perturb_free(&pt); + thermodynamics_free(&th); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + if (nonlinear_init(ppr,pba,pth,ppt,ppm,pnl) == _FAILURE_) { + printf("\n\nError in nonlinear_init \n=>%s\n",pnl->error_message); + primordial_free(&pm); + perturb_free(&pt); + thermodynamics_free(&th); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + if (transfer_init(ppr,pba,pth,ppt,pnl,ptr) == _FAILURE_) { + printf("\n\nError in transfer_init \n=>%s\n",ptr->error_message); + nonlinear_free(&nl); + primordial_free(&pm); + perturb_free(&pt); + thermodynamics_free(&th); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + if (spectra_init(ppr,pba,ppt,ppm,pnl,ptr,psp) == _FAILURE_) { + printf("\n\nError in spectra_init \n=>%s\n",psp->error_message); + transfer_free(&tr); + nonlinear_free(&nl); + primordial_free(&pm); + perturb_free(&pt); + thermodynamics_free(&th); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + if (lensing_init(ppr,ppt,psp,pnl,ple) == _FAILURE_) { + printf("\n\nError in lensing_init \n=>%s\n",ple->error_message); + spectra_free(&sp); + transfer_free(&tr); + nonlinear_free(&nl); + primordial_free(&pm); + perturb_free(&pt); + thermodynamics_free(&th); + background_free(&ba); + dofree=false; + return _FAILURE_; + } + + + dofree=true; + return _SUCCESS_; +} + + +int ClassEngine::computeCls(){ + +#ifdef DBUG + cout <<"call computecls" << endl; + //printFC(); +#endif + + int status=this->class_main(&fc,&pr,&ba,&th,&pt,&tr,&pm,&sp,&nl,&le,&op,_errmsg); +#ifdef DBUG + cout <<"status=" << status << endl; +#endif + return status; + +} + +int +ClassEngine::freeStructs(){ + + + if (lensing_free(&le) == _FAILURE_) { + printf("\n\nError in spectra_free \n=>%s\n",le.error_message); + return _FAILURE_; + } + + if (nonlinear_free(&nl) == _FAILURE_) { + printf("\n\nError in nonlinear_free \n=>%s\n",nl.error_message); + return _FAILURE_; + } + + if (spectra_free(&sp) == _FAILURE_) { + printf("\n\nError in spectra_free \n=>%s\n",sp.error_message); + return _FAILURE_; + } + + if (primordial_free(&pm) == _FAILURE_) { + printf("\n\nError in primordial_free \n=>%s\n",pm.error_message); + return _FAILURE_; + } + + if (transfer_free(&tr) == _FAILURE_) { + printf("\n\nError in transfer_free \n=>%s\n",tr.error_message); + return _FAILURE_; + } + + if (perturb_free(&pt) == _FAILURE_) { + printf("\n\nError in perturb_free \n=>%s\n",pt.error_message); + return _FAILURE_; + } + + if (thermodynamics_free(&th) == _FAILURE_) { + printf("\n\nError in thermodynamics_free \n=>%s\n",th.error_message); + return _FAILURE_; + } + + if (background_free(&ba) == _FAILURE_) { + printf("\n\nError in background_free \n=>%s\n",ba.error_message); + return _FAILURE_; + } + + return _SUCCESS_; +} + +void ClassEngine::call_perturb_sources_at_tau( + int index_md, + int index_ic, + int index_tp, + double tau, + double * psource + ) { + if( perturb_sources_at_tau( &pt, index_md, index_ic, index_tp, tau, psource ) == _FAILURE_){ + cerr << ">>>fail getting Tk type=" << (int)index_tp <& k, + std::vector& d_cdm, + std::vector& d_b, + std::vector& d_ncdm, + std::vector& d_tot, + std::vector& t_cdm, + std::vector& t_b, + std::vector& t_ncdm, + std::vector& t_tot ) +{ + + if (!dofree) throw out_of_range("no Tk available because CLASS failed"); + + double tau; + int index; + //transform redshift in conformal time + background_tau_of_z(&ba,z,&tau); + + if(log(tau) < pt.ln_tau[0]){ + cerr << "Asking sources at a z bigger than z_max_pk, something probably went wrong\n"; + throw out_of_range(pt.error_message); + } + + double *pvecback=new double[ba.bg_size]; + background_at_tau(&ba,tau,ba.long_info,ba.inter_normal, &index, pvecback); + double fHa = pvecback[ba.index_bg_f] * (pvecback[ba.index_bg_a]*pvecback[ba.index_bg_H]); + delete[] pvecback; + + // copy transfer func data to temporary + const size_t index_md = pt.index_md_scalars; + d_cdm.assign( pt.k_size[index_md], 0.0 ); + d_b.assign( pt.k_size[index_md], 0.0 ); + d_ncdm.assign( pt.k_size[index_md], 0.0 ); + d_tot.assign( pt.k_size[index_md], 0.0 ); + t_cdm.assign( pt.k_size[index_md], 0.0 ); + t_b.assign( pt.k_size[index_md], 0.0 ); + t_ncdm.assign( pt.k_size[index_md], 0.0 ); + t_tot.assign( pt.k_size[index_md], 0.0 ); + + if( pt.ic_size[index_md] > 1 ){ + cerr << ">>>have more than 1 ICs, will use first and ignore others" << endl; + } + + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_delta_cdm, tau, &d_cdm[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_delta_b, tau, &d_b[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_delta_ncdm1, tau, &d_ncdm[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_delta_tot, tau, &d_tot[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_theta_b, tau, &t_b[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_theta_ncdm1, tau, &t_ncdm[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_theta_tot, tau, &d_tot[0]); + + // + std::vector h_prime(pt.k_size[index_md],0.0), eta_prime(pt.k_size[index_md],0.0); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_eta_prime, tau, &eta_prime[0]); + call_perturb_sources_at_tau(index_md, 0, pt.index_tp_h_prime, tau, &h_prime[0]); + + // gauge trafo velocities, store k-vector + for (int index_k=0; index_k(l),cl) == _FAILURE_){ + cerr << ">>>fail getting Cl type=" << (int)t << " @l=" << l <& lvec, //input + std::vector& cltt, + std::vector& clte, + std::vector& clee, + std::vector& clbb) +{ + cltt.resize(lvec.size()); + clte.resize(lvec.size()); + clee.resize(lvec.size()); + clbb.resize(lvec.size()); + + for (size_t i=0;i& lvec, //input + std::vector& clpp , + std::vector& cltp , + std::vector& clep ){ + + + clpp.resize(lvec.size()); + cltp.resize(lvec.size()); + clep.resize(lvec.size()); + + for (size_t i=0;i +#include +#include +#include + +using std::string; + +//general utility to convert safely numerical types to string +template std::string str(const T &x); +//specialisations +template<> std::string str (const float &x); +template<> std::string str (const double &x); +template<> std::string str (const bool &x); //"yes" or "no" +template<> std::string str (const std::string &x); + +std::string str(const char* x); +////////////////////////////////////////////////////////////////////////// +//class to encapsulate CLASS parameters from any type (numerical or string) +class ClassParams{ +public: + + ClassParams(){}; + ClassParams( const ClassParams& o):pars(o.pars){}; + + //use this to add a CLASS variable + template unsigned add(const string& key,const T& val){ + pars.push_back(make_pair(key,str(val))); + return pars.size(); + } + + //accesors + inline unsigned size() const {return pars.size();} + inline string key(const unsigned& i) const {return pars[i].first;} + inline string value(const unsigned& i) const {return pars[i].second;} + + +private: + std::vector > pars; +}; + +/////////////////////////////////////////////////////////////////////////// +class ClassEngine : public Engine +{ + + friend class ClassParams; + +public: + //constructors + ClassEngine(const ClassParams& pars, bool verbose=true ); + //with a class .pre file + ClassEngine(const ClassParams& pars, const string & precision_file, bool verbose=true); + + + // destructor + ~ClassEngine(); + + //modfiers: _FAILURE_ returned if CLASS pb: + bool updateParValues(const std::vector& par); + + + //get value at l ( 2& lVec, //input + std::vector& cltt, + std::vector& clte, + std::vector& clee, + std::vector& clbb); + bool getLensing(const std::vector& lVec, //input + std::vector& clphiphi, + std::vector& cltphi, + std::vector& clephi); + + void call_perturb_sources_at_tau( + int index_md, + int index_ic, + int index_tp, + double tau, + double * psource + ); + + void getTk( double z, + std::vector& k, + std::vector& d_cdm, + std::vector& d_b, + std::vector& d_ncdm, + std::vector& d_tot, + std::vector& t_cdm, + std::vector& t_b, + std::vector& t_ncdm, + std::vector& t_tot ); + + //for BAO + inline double z_drag() const {return th.z_d;} + inline double rs_drag() const {return th.rs_d;} + double get_Dv(double z); + + double get_Da(double z); + double get_sigma8(double z); + double get_f(double z); + + double get_Fz(double z); + double get_Hz(double z); + double get_Az(double z); + + double getTauReio() const {return th.tau_reio;} + + //may need that + inline int numCls() const {return sp.ct_size;}; + inline double Tcmb() const {return ba.T_cmb;} + + inline int l_max_scalars() const {return _lmax;} + + //print content of file_content + void printFC(); + +private: + //structures class en commun + struct file_content fc; + struct precision pr; /* for precision parameters */ + struct background ba; /* for cosmological background */ + struct thermo th; /* for thermodynamics */ + struct perturbs pt; /* for source functions */ + struct transfers tr; /* for transfer functions */ + struct primordial pm; /* for primordial spectra */ + struct spectra sp; /* for output spectra */ + struct nonlinear nl; /* for non-linear spectra */ + struct lensing le; /* for lensed spectra */ + struct output op; /* for output files */ + + ErrorMsg _errmsg; /* for error messages */ + double * cl; + + //helpers + bool dofree; + int freeStructs(); + + //call once /model + int computeCls(); + + int class_main( + struct file_content *pfc, + struct precision * ppr, + struct background * pba, + struct thermo * pth, + struct perturbs * ppt, + struct transfers * ptr, + struct primordial * ppm, + struct spectra * psp, + struct nonlinear * pnl, + struct lensing * ple, + struct output * pop, + ErrorMsg errmsg); + //parnames + std::vector parNames; + +protected: + + +}; + +#endif + diff --git a/class/cpp/Engine.cc b/class/cpp/Engine.cc new file mode 100644 index 00000000..12b3ac98 --- /dev/null +++ b/class/cpp/Engine.cc @@ -0,0 +1,70 @@ +//-------------------------------------------------------------------------- +// +// Description: +// class Engine : see header file (Engine.hh) for description. +// +//------------------------------------------------------------------------ +//----------------------- +// This Class's Header -- +//----------------------- +#include "Engine.hh" +// ------------------------ +// Collaborating classes -- +//------------------------- +//-------------------- +// C++ +//-------------------- +#include +#include +#include +//-------------------- +// C +//---------------- + +using namespace std; +//--------------- +// Constructors -- +//---------------- +Engine::Engine():_lmax(-1) +{ +} +//-------------- +// Destructor -- +//-------------- + +//----------------- +// Member functions -- +//----------------- + +void +Engine::writeCls(std::ostream &of){ + + vector lvec(_lmax-1,1); + lvec[0]=2; + partial_sum(lvec.begin(),lvec.end(),lvec.begin()); + + vector cltt,clte,clee,clbb,clpp,cltp,clep; + bool hasLensing=false; + try{ + getCls(lvec,cltt,clte,clee,clbb); + hasLensing=getLensing(lvec,clpp,cltp,clep); + } + catch (std::exception &e){ + cout << "GIOSH" << e.what() << endl; + } + + cout.precision( 16 ); + for (size_t i=0;i +#include + +class Engine +{ + +public: + + enum cltype {TT=0,EE,TE,BB,PP,TP,EP}; //P stands for phi (lensing potential) + + //constructors + Engine(); + + //pure virtual: + virtual bool updateParValues(const std::vector& cosmopars)=0; + + // units = (micro-K)^2 + virtual void getCls(const std::vector& lVec, //input + std::vector& cltt, + std::vector& clte, + std::vector& clee, + std::vector& clbb)=0; + + + virtual bool getLensing(const std::vector& lVec, //input + std::vector& clpp, + std::vector& cltp, + std::vector& clep)=0; + + + virtual double z_drag() const=0; + virtual double rs_drag() const =0; + + virtual double get_Dv(double z)=0; + + virtual double get_Da(double z)=0; + virtual double get_sigma8(double z)=0; + virtual double get_f(double z)=0; + virtual double get_Fz(double z)=0; + virtual double get_Az(double z)=0; + virtual double get_Hz(double z)=0; + + virtual double getTauReio() const=0; + + // destructor + virtual ~Engine(){}; + + //write Cl model+lensing in ostream + virtual void writeCls(std::ostream &o); + inline int lmax() {return _lmax;} + +protected: + int _lmax; + +}; + +#endif + diff --git a/class/cpp/Makefile b/class/cpp/Makefile new file mode 100644 index 00000000..255eca95 --- /dev/null +++ b/class/cpp/Makefile @@ -0,0 +1,28 @@ +CXX = g++ +CFLAGS = -O2 -fopenmp -I../include +CLASSMODULES = ../build/arrays.o ../build/background.o ../build/common.o \ + ../build/dei_rkck.o ../build/evolver_ndf15.o ../build/evolver_rkck.o \ + ../build/growTable.o ../build/helium.o ../build/history.o \ + ../build/hydrogen.o ../build/hyperspherical.o ../build/hyrectools.o \ + ../build/input.o ../build/lensing.o ../build/nonlinear.o ../build/output.o \ + ../build/parser.o ../build/perturbations.o ../build/primordial.o \ + ../build/quadrature.o ../build/sparse.o ../build/spectra.o \ + ../build/thermodynamics.o ../build/transfer.o \ + ../build/trigonometric_integrals.o + +all: testKlass Makefile + +testKlass: testKlass.o Engine.o ClassEngine.o + $(CXX) $(CFLAGS) $(CLASSMODULES) ClassEngine.o Engine.o testKlass.o -o testKlass + +testKlass.o: testKlass.cc + $(CXX) $(CFLAGS) -c testKlass.cc -o testKlass.o + +ClassEngine.o: ClassEngine.cc ClassEngine.hh + $(CXX) $(CFLAGS) -c ClassEngine.cc -o ClassEngine.o + +Engine.o: Engine.cc Engine.hh + $(CXX) $(CFLAGS) -c Engine.cc -o Engine.o + +clean: + rm -rf *.o testKlass diff --git a/class/cpp/README b/class/cpp/README new file mode 100644 index 00000000..0bb49733 --- /dev/null +++ b/class/cpp/README @@ -0,0 +1,11 @@ +The C++ wrapper ClassEngine.cc for Class (written by S. Plaszczynski) is distributed together with a test code, testKlass.cc, in which you can write a list of input parameters. This test code can be compiled with (assuming you are already in the directory cpp/ and you have a c++ compiler compatible with openmp): + +> c++ -O2 -fopenmp -I../include -c Engine.cc -o Engine.o +> c++ -O2 -fopenmp -I../include -c ClassEngine.cc -o ClassEngine.o +> c++ -O2 -fopenmp -I../include -c testKlass.cc -o testKlass.o +> cd .. +> c++ -O2 -fopenmp build/arrays.o build/background.o build/common.o build/dei_rkck.o build/evolver_ndf15.o build/evolver_rkck.o build/growTable.o build/helium.o build/history.o build/hydrogen.o build/hyperspherical.o build/hyrectools.o build/input.o build/lensing.o build/nonlinear.o build/output.o build/parser.o build/perturbations.o build/primordial.o build/quadrature.o build/sparse.o build/spectra.o build/thermodynamics.o build/transfer.o cpp/ClassEngine.o cpp/Engine.o cpp/testKlass.o -o testKlass + +then run with: + +> ./testKlass diff --git a/class/cpp/testKlass.cc b/class/cpp/testKlass.cc new file mode 100644 index 00000000..23f120e4 --- /dev/null +++ b/class/cpp/testKlass.cc @@ -0,0 +1,71 @@ + +//KLASS +#include"ClassEngine.hh" + +#include +#include +#include +#include + +using namespace std; + + +// example run: one can specify as a second argument a preicison file +int main(int argc,char** argv){ + + const int l_max_scalars=1200; + + //CLASS config + ClassParams pars; + + pars.add("100*theta_s",1.04); + pars.add("omega_b",0.0220); + pars.add("omega_cdm",0.1116); + pars.add("A_s",2.42e-9); + pars.add("n_s",.96); + pars.add("tau_reio",0.09); + + pars.add("k_pivot",0.05); + pars.add("YHe",0.25); + pars.add("output","tCl,pCl,lCl"); //pol +clphi + + pars.add("l_max_scalars",l_max_scalars); + pars.add("lensing",true); //note boolean + + pars.add("background_verbose",1); + pars.add("thermodynamics_verbose",1); + pars.add("perturbations_verbose",1); + pars.add("transfer_verbose",1); + pars.add("primordial_verbose",1); + pars.add("spectra_verbose",1); + pars.add("nonlinear_verbose",1); + pars.add("lensing_verbose",1); + + ClassEngine* KKK(0); + + try{ + //le calculateur de spectres + if (argc==2){ + string pre=string(argv[1]); + KKK=new ClassEngine(pars,pre); + } + else{ + KKK=new ClassEngine(pars); + } + + //cout.precision( 16 ); + //KKK->writeCls(cout); + + ofstream outfile; + const char* outfile_name = "testKlass_Cl_lensed.dat"; + outfile.open(outfile_name, ios::out | ios::trunc ); + KKK->writeCls(outfile); + cout << "Cl's written in file " << outfile_name << endl; + } + catch (std::exception &e){ + cout << "GOSH" << e.what() << endl; + } + + delete KKK; + +} diff --git a/class/doc/README b/class/doc/README new file mode 100644 index 00000000..71313830 --- /dev/null +++ b/class/doc/README @@ -0,0 +1,13 @@ +CLASS automatic documentation folders +===================================== +(Deanna Hooper, 25.03.2016) + +* the automatically generated PDF manual can be found in + + doc/manual/CLASS_MANUAL.pdf + +* the files in doc/input/ are auxiliary files for generating it + +* if you wish to update this manual yourself using doxygen, look at instructions in section 6 of CLASS_MANUAL.pdf + +* there is also an html version that you can access from the CLASS webpages. The html version used to be distributed together with CLASS, but we removed it because the html directory was too big. If you do wish to get the html source files on your own computer, you just need to recompile the manual with "cd doc/input/; ./make1.sh" (assuming that you have doxygen installed). \ No newline at end of file diff --git a/class/doc/input/chap2.md b/class/doc/input/chap2.md new file mode 100644 index 00000000..244374bc --- /dev/null +++ b/class/doc/input/chap2.md @@ -0,0 +1,108 @@ +Where to find information and documentation on CLASS? +====================================================== + +Author: Julien Lesgourgues + + +* __For what the code can actually compute__: all possible input parameters, all coded cosmological models, all functionalities, all observables, etc.: read the file `explanatory.ini` in the main `CLASS` directory: it is THE reference file where we keep track of all possible input and the definition of all input parameters. For that reason we recommend to leave it always unchanged and to work with copies of it, or with short input files written from scratch. + + +* __For the structure, style, and concrete aspects of the code__: this documentation, especially the `CLASS overview` chapter (the extensive automatically-generated part of this documentation is more for advanced users); plus the slides of our `CLASS` lectures, for instance those from Tokyo 2014 available at + + `http://lesgourg.github.io/class-tour-Tokyo.html` + + or the more recent and concise summary from the Narbonne 2016 lecture available at + + `http://lesgourg.github.io/class-tour/Narbonne.pdf` + + An updated overview of available `CLASS` lecture slides is always available at + + `http://lesgourg.github.io/courses.html` + + in the section `Courses on numerical tools`. + + +* __For the python wrapper of `CLASS`__: at the moment, the best are the last slides (pages 75-96) of the Narbonne 2016 lectures + + `http://lesgourg.github.io/class-tour/Narbonne.pdf` + + Later we will expand the wrapper documentation with a dedicated chapter here. + +* __For the physics and equations used in the code__: mainly, the following papers: + - *Cosmological perturbation theory in the synchronous and conformal Newtonian gauges* + + C. P. Ma and E. Bertschinger. + + http://arxiv.org/abs/astro-ph/9506072 + + 10.1086/176550 + + Astrophys. J. __455__, 7 (1995) + + - *The Cosmic Linear Anisotropy Solving System (CLASS) II: Approximation schemes* + + D. Blas, J. Lesgourgues and T. Tram. + + http://arxiv.org/abs/1104.2933 [astro-ph.CO] + + 10.1088/1475-7516/2011/07/034 + + JCAP __1107__, 034 (2011) + + - *The Cosmic Linear Anisotropy Solving System (CLASS) IV: efficient implementation of non-cold relics* + + J. Lesgourgues and T. Tram. + + http://arxiv.org/abs/1104.2935 [astro-ph.CO] + + 10.1088/1475-7516/2011/09/032 + + JCAP __1109__, 032 (2011) + + - *Optimal polarisation equations in FLRW universes* + + T. Tram and J. Lesgourgues. + + http://arxiv.org/abs/1305.3261 [astro-ph.CO] + + 10.1088/1475-7516/2013/10/002 + + JCAP __1310__, 002 (2013) + + - *Fast and accurate CMB computations in non-flat FLRW universes* + + J. Lesgourgues and T. Tram. + + http://arxiv.org/abs/1312.2697 [astro-ph.CO] + + 10.1088/1475-7516/2014/09/032 + + JCAP __1409__, no. 09, 032 (2014) + + - *The CLASSgal code for Relativistic Cosmological Large Scale Structure* + + E. Di Dio, F. Montanari, J. Lesgourgues and R. Durrer. + + http://arxiv.org/abs/1307.1459 [astro-ph.CO] + + 10.1088/1475-7516/2013/11/044 + + JCAP __1311__, 044 (2013) + + plus also some latex notes on specific sectors: + + - *Equations for perturbed recombination* + + (can be turned on optionally by the user since v2.1.0) + + L. Voruz. + + http://lesgourg.github.io/class_public/perturbed_recombination.pdf + + - *PPF formalism in Newtonian and synchronous gauge* + + (used by default for the fluid perturbations since v2.6.0) + + T. Tram. + + http://lesgourg.github.io/class_public/PPF_formalism.pdf \ No newline at end of file diff --git a/class/doc/input/chap3.md b/class/doc/input/chap3.md new file mode 100644 index 00000000..1e79b6b5 --- /dev/null +++ b/class/doc/input/chap3.md @@ -0,0 +1,517 @@ +CLASS overview (architecture, input/output, general principles) +=============================================================== + +Author: Julien Lesgourgues + + +# Overall architecture of `class` # + +## Files and directories ## + +After downloading `CLASS`, one can see the following files in the root directory contains: + +- some example of input files, the most important being `explanatory.ini`. a reference input file containing all possible flags, options and physical input parameters. While this documentation explains the structure and use of the code, `explanatory.ini` can be seen as the _physical_ documentation of `CLASS`. The other input file are alternative parameter input files (ending with `.ini`) and precision input files (ending with `.pre`) + +- the `Makefile`, with which you can compile the code by typing `make clean; make;` this will create the executable `class` and some binary files in the directory `build/`. The `Makefile` contains other compilation options that you can view inside the file. + +- `CPU.py` is a python script designed for plotting the `CLASS` output; for documentation type `python CPU.py --help` + +- `plot_CLASS_output.m` is the counterpart of `CPU.py` for MatLab + +- there are other input files for various applications: an example of a non-cold dark matter distribution functions (`psd_FD_single.dat`), and examples of evolution and selection functions for galaxy number count observables (`myevolution.dat, myselection.dat`). + +Other files are split between the following directories: + +- `source/` contains the C files for each `CLASS` module, i.e. each +block containing some part of the physical equations and logic of +the Boltzmann code. + +- `tools/` contains purely numerical algorithms, applicable in any +context: integrators, simple manipulation of arrays (derivation, +integration, interpolation), Bessel function calculation, quadrature algorithms, parser, etc. + +- `main/` contains the main module `class.c` with the main + routine `class(...)`, to be used in interactive runs (but not + necessarily when the code is interfaced with other ones). + +- `test/` contains alternative main routines which can be used to run only some part of the code, to test its accuracy, to illustrate how +it can be interfaced with other codes, etc. + +- `include/` contains all the include files with a `.h` suffix. + +- `output/` is where the output files will be written by default (this can be changed to another directory by adjusting the input parameter `root = <...>`) + +- `python/` contains the python wrapper of `CLASS`, called classy (see `python/README`) + +- `cpp/` contains the C++ wrapper of `CLASS`, called ClassEngine (see `cpp/README`) + +- `doc/` contains the automatic documentation (manual and input files required to build it) + +- `external_Pk/` contains examples of external codes that can be used to generate the primordial spectrum and be interfaced with `CLASS`, when one of the many options already built inside the code are not sufficient. + +- `bbn/` contains interpolation tables produced by BBN codes, in order to predict e.g. \f$ Y_\mathrm{He}(\omega_b, \Delta N_\mathrm{eff})\f$. + +- `hyrec/` contains the recombination code HyRec of Yacine Ali-Haimoud and Chris Hirata, that can be used as an alternative to the built-in Recfast (using the input parameter `recombination = <...>`). + + +## The ten-module backbone ## + +### Ten tasks ### + +The purpose of `class` consists in computing some background quantities, thermodynamical quantities, perturbation transfer functions, and finally 2-point statistics (power spectra) for a given set of cosmological parameters. This task can be decomposed in few steps or modules: + +1. set input parameter values. + +2. compute the evolution of cosmological background quantities. + +3. compute the evolution of thermodynamical quantities (ionization fractions, etc.) + +4. compute the evolution of source functions \f$S(k,\tau)\f$ (by integrating over all perturbations). + +5. compute the primordial spectra. + +6. eventually, compute non-linear corrections at small redshift/large wavenumber. + +7. compute transfer functions in harmonic space \f$\Delta_l(k)\f$ (unless one needs only Fourier spectra \f$P(k)\f$'s and no harmonic spectra \f$C_l\f$'s). + +8. compute the observable power spectra \f$C_l\f$'s (by convolving the primordial spectra and the harmonic transfer functions) and/or \f$P(k)\f$'s (by multiplying the primordial spectra and the appropriate source functions \f$S(k,\tau)\f$). + +9. eventually, compute the lensed CMB spectra (using second-order perturbation theory) + +10. write results in files (when `CLASS` is used interactively. The python wrapper does not go through this step, after 1.-9. it just keeps the output stored internally). + + +### Ten structures ### + +In `class`, each of these steps is associated with a structure: + +1. `struct precision` for input precision parameters (input physical parameters are dispatched among the other structures listed below) +2. `struct background` for cosmological background, +3. `struct thermo` for thermodynamics, +4. `struct perturbs` for source functions, +5. `struct primordial` for primordial spectra, +6. `struct nonlinear` for nonlinear corrections, +7. `struct transfers` for transfer functions, +8. `struct spectra` for observable spectra, +9. `struct lensing` for lensed CMB spectra, +10. `struct output` for auxiliary variable describing the output format. + +A given structure contains "everything concerning one step that the +subsequent steps need to know" (for instance, `struct perturbs` contains everything about source +functions that the transfer module needs to know). In particular, each +structure contains one array of tabulated values (for `struct background`, background +quantities as a function of time, for `struct thermo`, thermodynamical quantities as a +function of redshift, for `struct perturbs`, sources \f$S(k, \tau)\f$, etc.). It +also contains information about the size of this array and the value +of the index of each physical quantity, so that the table can be +easily read and interpolated. Finally, it contains any derived +quantity that other modules might need to know. Hence, the +communication from one module A to another module B +consists in passing a pointer to the structure filled by A, and nothing else. + +All "precision parameters" are grouped in the single structure +`struct precision`. The code contains _no other arbitrary +numerical coefficient_. + +### Ten modules ### + +Each structure is defined and filled in one of the following modules +(and precisely in the order below): + +1. `input.c` +2. `background.c` +3. `thermodynamics.c` +4. `perturbations.c ` +5. `primordial.c` +6. `nonlinear.c` +7. `transfer.c` +8. `spectra.c` +9. `lensing.c` +10. `output.c` + + +Each of these modules contains at least three functions: + +- `module_init(...)` + +- `module_free(...)` + +- `module_something_at_somevalue` + +where _module_ is one of `input, background, thermodynamics, perturb, primordial, nonlinear, transfer, spectra, lensing, output`. + + +The first function allocates and fills each structure. This can be +done provided that the previous structures in the hierarchy have been +already allocated and filled. In summary, calling one of `module_init(...)` amounts in solving entirely one of the steps 1 to 10. + +The second function deallocates the fields of each structure. This +can be done optionally at the end of the code (or, when the code is embedded +in a sampler, this __must__ be done +between each execution of `class`, and especially before calling `module_init(...)` again with different input parameters). + +The third function is able to interpolate the pre-computed tables. For +instance, `background_init()` fills a table of background +quantities for discrete values of conformal time \f$\tau\f$, but +`background_at_tau(tau, * values)` will return these values for any +arbitrary \f$\tau\f$. + +Note that functions of the type `module_something_at_somevalue` are the only ones which are +called from another module, while functions of the type `module_init(...)` and `module_free(...)` are the only +one called by the main executable. All other functions are for +internal use in each module. + +When writing a C code, the ordering of the functions in the *.c file is in principle arbitrary. However, for the sake of clarity, we always respected the following order in each `CLASS` module: + +1. all functions that may be called by other modules, i.e. "external functions", usually named like `module_something_at_somevalue(...)` +2. then, `module_init(...)` +3. then, `module_free()` +4. then, all functions used only internally by the module + + +## The `main()` function(s) ## + +### The `main.c` file ### + +The main executable of `class` is the function `main()` located in the file `main/main.c`. +This function consist only in the +following lines +(not including comments and error-management lines explained later): + + main() { + struct precision pr; + + struct background ba; + + struct thermo th; + + struct perturbs pt; + + struct primordial pm; + + struct nonlinear nl; + + struct transfers tr; + + struct spectra sp; + + struct lensing le; + + struct output op; + + + input_init_from_arguments(argc, argv,&pr,&ba,&th,&pt,&tr,&pm,&sp,&nl,&le,&op,errmsg); + + background_init(&pr,&ba); + + thermodynamics_init(&pr,&ba,&th); + + perturb_init(&pr,&ba,&th,&pt); + + primordial_init(&pr,&pt,&pm); + + nonlinear_init(&pr,&ba,&th,&pt,&pm,&nl); + + transfer_init(&pr,&ba,&th,&pt,&nl,&tr); + + spectra_init(&pr,&ba,&pt,&pm,&nl,&tr,&sp); + + lensing_init(&pr,&pt,&sp,&nl,&le); + + output_init(&ba,&th,&pt,&pm,&tr,&sp,&nl,&le,&op) + + + /****** done ******/ + + + lensing_free(&le); + + spectra_free(&sp); + + transfer_free(&tr); + + nonlinear_free(&nl); + + primordial_free(&pm); + + perturb_free(&pt); + + thermodynamics_free(&th); + + background_free(&ba); + + +We can come back on the role of each argument. The arguments above are all pointers to the 10 structures of the code, excepted `argc, argv` which contains the input files passed by the user, and `errmsg` which contains the output error message of the input module (error management will be described below). + +`input_init_from_arguments` needs all structures, because it will set the precision parameters inside the `precision` structure, and the physical parameters in some fields of the respective other structures. For instance, an input parameter relevant for the primordial spectrum calculation (like the tilt \f$n_s\f$) will be stored in the `primordial` structure. Hence, in ` input_init_from_arguments`, all structures can be seen as output arguments. + +Other `module_init()` functions typically need all previous structures, which contain the result of the previous modules, plus its own structures, which contain some relevant input parameters before the function is called, as well as all the result form the module when the function has been executed. Hence all passed structures can be seen as input argument, excepted the last one which is both input and output. An example is `perturb_init(&pr,&ba,&th,&pt)`. + +Each function `module_init()` does not need __all__ previous structures, it happens that a module does not depend on a __all__ previous one. For instance, the primordial module does not need information on the background and thermodynamics evolution in order to compute the primordial spectra, so the dependency is reduced: `primordial_init(&pr,&pt,&pm)`. + +Each function `module_init()` only deallocates arrays defined in the structure of their own module, so they need only their own structure as argument. (This is possible because all structures are self-contained, in the sense that when the structure contains an allocated array, it also contains the size of this array). The first and last module, `input` and `output`, have no `input_free()` or `output_free()` functions, because the structures `precision` and `output` do not contain arrays that would need to be de-allocated after the execution of the module. + +### The `test_<...>.c` files ### + +For a given purpose, somebody could only be interested in the +intermediate steps (only background quantities, only the +thermodynamics, only the perturbations and sources, etc.) It is +then straightforward to truncate the full hierarchy of modules 1, ... 10 at some +arbitrary order. We provide several "reduced executables" achieving precisely this. +They are located in `test/test_module_.c` (like, for instance, `test/test_perturbations.c`) and they can +be complied using the Makefile, which contains the appropriate commands and definitions (for instance, you can type `make test_perturbations`). + +The `test/` directory contains other useful example of alternative main functions, like for instance +`test_loops.c` which shows how to call `CLASS` within a loop over different parameter values. +There is also a version `test/test_loops_omp.c` using a double level of openMP parallelisation: one for running several `CLASS` instances in parallel, one for running each `CLASS` instance on several cores. The comments in these files are self-explanatory. + +# Input/output # + +## Input ## + +There are two types of input: + +- "precision parameters" (controlling the precision of the output and the execution time), + +- "input parameters" (cosmological parameters, flags telling to the code what it should compute, ...) + +The code can be executed with a maximum of two input files, e.g. + + ./class explanatory.ini cl_permille.pre + + +The file with a `.ini` extension is the cosmological parameter +input file, and the one with a `.pre` extension is the precision +file. Both files are optional: all parameters are set to default +values corresponding to the "most usual choices", and are eventually +replaced by the parameters passed in the two input files. For +instance, if one is happy with default accuracy settings, it is enough +to run with + + ./class explanatory.ini + +Input files do not +necessarily contain a line for each parameter, since many of them can +be left to default value. The example file `explanatory.ini` is +very long and somewhat indigestible, since it contains all possible +parameters, together with lengthy explanations. We recommend to keep +this file unchanged for reference, and to copy it in e.g. `test.ini`. +In the latter file, the user can erase all sections in +which he/she is absolutely not interested (e.g., all the part on +isocurvature modes, or on tensors, or on non-cold species, +etc.). Another option is to create an input file from scratch, copying +just the relevant lines from `explanatory.ini`. For the simplest +applications, the user will just need a few lines for basic +cosmological parameters, one line for the `output` entry (where +one can specifying which power spectra must be computed), and one line +for the `root` entry (specifying the prefix of all output files). + +The syntax of the input files is explained at the beginning of +`explanatory.ini`. Typically, lines in those files look like: + + + parameter1 = value1 + + free comments + + parameter2 = value2 # further comments + + # commented_parameter = commented_value + +and parameters can be entered in arbitrary order. This is rather +intuitive. The user should just be careful not to put an "=" +sign not preceded by a "#" sign inside a comment: the code +would then think that one is trying to pass some unidentified input +parameter. + +The syntax for the cosmological and precision parameters is the same. +It is clearer to split these parameters in the two files `.ini` +and `.pre`, but there is no strict rule about which parameter goes +into which file: in principle, precision parameters could be passed in +the `.ini`, and vice-versa. The only important thing is not to pass +the same parameter twice: the code would then complain and not run. + +The `CLASS` input files are also user-friendly in the sense that many +different cosmological parameter bases can be used. This is made +possible by the fact that the code does not only read parameters, it +"interprets them" with the level of logic which has been coded in +the `input.c` module. For instance, the Hubble parameter, the photon +density, the baryon density and the ultra-relativistic neutrino density can be +entered as: + + h = 0.7 + + T_cmb = 2.726 # Kelvin units + + omega_b = 0.02 + + N_eff = 3.04 + + +(in arbitrary order), or as + + + H0 = 70 + + omega_g = 2.5e-5 # g is the label for photons + + Omega_b = 0.04 + + omega_ur = 1.7e-5 # ur is the label for ultra-relativistic species + + +or any combination of the two. The code knows that for the photon +density, one should pass one (but not more than one) parameter out of +`T_cmb`, `omega_g`, `Omega_g` (where small omega's refer to +\f$\omega_i \equiv \Omega_i h^2\f$). It searches for one of these values, +and if needed, it converts it into one of the other two parameters, +using also other input parameters. For instance, `omega_g` will +be converted into `Omega_g` even if \f$h\f$ is written later in the +file than `omega_g`: the order makes no difference. Lots of +alternatives have been defined. If the code finds that not enough +parameters have been passed for making consistent deductions, it will +complete the missing information with in-built default values. On the +contrary, if it finds that there is too much information and no unique +solution, it will complain and return an error. + +In summary, the input syntax has been defined in such way that the +user does not need to think too much, and can pass his preferred set +of parameters in a nearly informal way. + +Let us mention a two useful parameters defined at the end of `explanatory.ini`, that we recommend setting to `yes` in order to run the code in a safe way: + +`write parameters = [yes or no]` (_default_: `no`) + +When set to yes, all input/precision parameters which have been read +are written in a file `parameters.ini`, to keep track all the details of this execution; this file can also be re-used as a new input file. Also, with this option, all parameters that have been passed and that the code did not read (because the syntax was wrong, or because the parameter was not relevant in the context of the run) are written in a file `unused_parameters`. When you have doubts about your input or your results, you can check what is in there. + +`write warnings = [yes or no]` (_default_: `no`) + +When set to yes, the parameters that have been passed and that the code did not read +(because the syntax was wrong, or because the parameter was not relevant in the context of the run) are written +in the standard output as `[Warning:]....` + +There is also a list of "verbose" parameters at the end of `explanatory.ini`. They can be used to control +the level of information passed to the standard output (0 means silent; 1 means normal, e.g. information on age of the universe, etc.; 2 is useful for instance when you want to check on how many cores the run is parallelised; 3 and more are intended for debugging). + +`CLASS` comes with a list of precision parameter files ending by `.pre`. Honestly we have not been updating all these files recently, and we need to do a bit of cleaning there. However you can trust `cl_ref.pre`. We have derived this file by studying both the convergence of the CMB output with respect to all `CLASS` precision parameters, and the agreement with `CAMB`. We consider that this file generates good reference CMB spectra, accurate up to the hundredth of per cent level, as explained in the CLASS IV paper and re-checked since then. You can try it with e.g. + + ./class explanatory.ini cl_ref.pre + +but the run will be extremely long. This is an occasion to run a many-core machine with a lot of RAM. It may work also on your laptop, but in half an hour or so. + +If you want a reference matter power spectrum P(k), also accurate up to the hundredth of percent level, we recommend using the file `pk_ref.pre`, identical to `cl_ref.pre` excepted that the truncation of the neutrino hierarchy has been pushed to `l_max_ur=150`. + +In order to increase moderately the precision to a tenth of percent, without prohibitive computing time, we recommend using `cl_permille.pre`. + +## Output ## + +The input file may contain a line + + root = + +where `` is a path of your choice, e.g. `output/test_`. +Then all output files will start like this, e.g. `output/test_cl.dat`, `output/test_cl_lensed.dat`, etc. +Of course the number of output files depends on your settings in the input file. There can be input files for CMB, LSS, background, thermodynamics, transfer functions, primordial spectra, etc. All this is documented in `explanatory.ini`. + +If you do not pass explicitly a `root = `, the code will name the output in its own way, by concatenating `output/`, the name of the input parameter file, and the first available integer number, e.g. + + output/explanatory03_cl.dat, etc. + + +# General principles # + +## Error management ## + +Error management is based on the fact that all functions are defined +as integers returning either `_SUCCESS_` or `_FAILURE_`. Before returning `_FAILURE_`, they write an +error message in the structure of the module to which they belong. The +calling function will read this message, append it to its own error +message, and return a `_FAILURE_`; and so on and so forth, until +the main routine is reached. This error management allows the user to +see the whole nested structure of error messages when an error has +been met. The structure associated to each module contains a field +for writing error messages, called `structure_i.error_message`, where `structure_i` could be one of `background`, `thermo`, `perturbs`, etc. So, when a function from a module \f$i\f$ +is called within module \f$j\f$ and returns an error, the goal is to write +in `structure_j.error_message` a local error message, and to +append to it the error message in `structure_i.error_message`. These steps are implemented in a macro `class_call()`, used for calling whatever function: + + + class_call(module_i_function(...,structure_i), + structure_i.error_message, + structure_j.error_message); + + +So, the first argument of `call_call()` is the function we want +to call; the second argument is the location of the error message +returned by this function; and the third one is the location of the +error message which should be returned to the higher level. +Usually, in the bulk of the code, we use pointer to structures rather than structure themselves; then the syntax is + + class_call(module_i_function(...,pi), + pi->error_message, + pj->error_message);` + +where in this generic example, `pi` and `pj` are assumed to be pointers towards the structures +`structure_i` and `structure_j`. + +The user will find in `include/common.h` a list of additional macros, all +starting by `class_...()`, which are all based on this logic. For +instance, the macro `class_test()` offers a generic way to return +an error in a standard format if a condition is not fulfilled. A +typical error message from `CLASS` looks like: + + +`Error in module_j_function1` + +`module_j_function1 (L:340) : error in module_i_function2(...)` + +`module_i_function2 (L:275) : error in module_k_function3(...)` + +`...` + +`=> module_x_functionN (L:735) : your choice of input parameter blabla=30 +is not consistent with the constraint blabla<1` + + +where the `L`'s refer to line numbers in each file. These error +messages are very informative, and are built almost entirely +automatically by the macros. For instance, in the above example, it +was only necessary to write inside the function `module_x_functionN()` a test like: + + + class_test(blabla >= 1, + px->error_message, + "your choice of input parameter blabla=%e + is not consistent with the constraint blabla<%e", + blabla,blablamax); + + +All the rest was added step by step by the various `class_call()` macros. + + +## Dynamical allocation of indices ## + +On might be tempted to decide that in a given array, matrix or vector, a given quantity is associated with an explicit index value. However, when modifying the code, extra entries will be needed and will mess up the initial scheme; the user will need to study which index is associated to which quantity, and possibly make an error. All this can be avoided by using systematically a dynamical index allocation. This means that all indices remain under a symbolic form, and in each, run the code attributes automatically a value to each index. The user never needs to know this value. + +Dynamical indexing is implemented in a very generic way in CLASS, the same rules apply everywhere. They are explained in these lecture slides: + +`https://www.dropbox.com/sh/ma5muh76sggwk8k/AABl_DDUBEzAjjdywMjeTya2a?dl=0` + +in the folder `CLASS_Lecture_slides/lecture5_index_and_error.pdf`. + +## No hard coding ## + +Any feature or equation which could be true in one cosmology and not in another one should not be written explicitly in the code, and should not be taken as granted in several other places. Discretization and integration steps are usually defined automatically by the code for each cosmology, instead of being set to something which might be optimal for minimal models, and not sufficient for other ones. You will find many example of this in the code. As a consequence, in the list of precision parameter, you rarely find actual stepsize. You find rather parameters representing the ratio between a stepsize and a physical quantity computed for each cosmology. + +## Modifying the code ## + +Implementing a new idea completly from scratch would be rather intimidating, even for the main developpers of `CLASS`. Fortunately, we never have to work from scratch. Usually we want to code a new species, a new observable, a new approximation scheme, etc. The trick is to think of another species, observable, approximation scheme, etc., looking as close as possible to the new one. + +Then, playing with the `grep` command and the `search` command of your editor, search for all occurences of this nearest-as-possible other feature. This is usually easy thanks to our naming scheme. For each species, observable, approximation scheme, etc., we usually use the same sequence of few letters everywhere (fo instance, `fld` for the fluid usually representing Dark Energy). Grep for `fld` and you'll get all the lines related to the fluid. There is another way: we use everywhere some conditional jumps related to a given feature. For instance, the lines related to the fluid are always in between `if (pba->has_fld == _TRUE_) { ... }` and the lines related to the cosmic shear observables are always in between `if (ppt->has_lensing_potential == _TRUE_) { ... }`. Locating these flags and conditional jumps shows you all the parts related to a given feature/ingredient. + +Once you have localised your nearest-as-possible other feature, you can copy/paste these lines and adapt them to the case of your new feature! You are then sure that you didn't miss any step, even the smallest technical steps (definition of indices, etc.) + +# Units # + +Internally, the code uses almost everywhere units of Mpc to some power, excepted in the inflation module, where many quantities are in natural units (wrt the true Planck mass). diff --git a/class/doc/input/doxyconf b/class/doc/input/doxyconf new file mode 100644 index 00000000..0c2a683b --- /dev/null +++ b/class/doc/input/doxyconf @@ -0,0 +1,2362 @@ +# Doxyfile 1.8.9.1 + +# This file describes the settings to be used by the documentation system +# doxygen (www.doxygen.org) for a project. +# +# All text after a double hash (##) is considered a comment and is placed in +# front of the TAG it is preceding. +# +# All text after a single hash (#) is considered a comment and will be ignored. +# The format is: +# TAG = value [value, ...] +# For lists, items can also be appended using: +# TAG += value [value, ...] +# Values that contain spaces should be placed between quotes (\" \"). + +#--------------------------------------------------------------------------- +# Project related configuration options +#--------------------------------------------------------------------------- + +# This tag specifies the encoding used for all characters in the config file +# that follow. The default is UTF-8 which is also the encoding used for all text +# before the first occurrence of this tag. Doxygen uses libiconv (or the iconv +# built into libc) for the transcoding. See http://www.gnu.org/software/libiconv +# for the list of possible encodings. +# The default value is: UTF-8. + +DOXYFILE_ENCODING = UTF-8 + +# The PROJECT_NAME tag is a single word (or a sequence of words surrounded by +# double-quotes, unless you are using Doxywizard) that should identify the +# project for which the documentation is generated. This name is used in the +# title of most generated pages and in a few other places. +# The default value is: My Project. + +PROJECT_NAME = "CLASS MANUAL" + +# The PROJECT_NUMBER tag can be used to enter a project or revision number. This +# could be handy for archiving the generated documentation or if some version +# control system is used. + +PROJECT_NUMBER = + +# Using the PROJECT_BRIEF tag one can provide an optional one line description +# for a project that appears at the top of each page and should give viewer a +# quick idea about the purpose of the project. Keep the description short. + +PROJECT_BRIEF = + +# With the PROJECT_LOGO tag one can specify a logo or an icon that is included +# in the documentation. The maximum height of the logo should not exceed 55 +# pixels and the maximum width should not exceed 200 pixels. Doxygen will copy +# the logo to the output directory. + +PROJECT_LOGO = + +# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) path +# into which the generated documentation will be written. If a relative path is +# entered, it will be relative to the location where doxygen was started. If +# left blank the current directory will be used. + +OUTPUT_DIRECTORY = ../manual + +# If the CREATE_SUBDIRS tag is set to YES then doxygen will create 4096 sub- +# directories (in 2 levels) under the output directory of each output format and +# will distribute the generated files over these directories. Enabling this +# option can be useful when feeding doxygen a huge amount of source files, where +# putting all generated files in the same directory would otherwise causes +# performance problems for the file system. +# The default value is: NO. + +CREATE_SUBDIRS = NO + +# If the ALLOW_UNICODE_NAMES tag is set to YES, doxygen will allow non-ASCII +# characters to appear in the names of generated files. If set to NO, non-ASCII +# characters will be escaped, for example _xE3_x81_x84 will be used for Unicode +# U+3044. +# The default value is: NO. + +ALLOW_UNICODE_NAMES = YES + +# The OUTPUT_LANGUAGE tag is used to specify the language in which all +# documentation generated by doxygen is written. Doxygen will use this +# information to generate all constant output in the proper language. +# Possible values are: Afrikaans, Arabic, Armenian, Brazilian, Catalan, Chinese, +# Chinese-Traditional, Croatian, Czech, Danish, Dutch, English (United States), +# Esperanto, Farsi (Persian), Finnish, French, German, Greek, Hungarian, +# Indonesian, Italian, Japanese, Japanese-en (Japanese with English messages), +# Korean, Korean-en (Korean with English messages), Latvian, Lithuanian, +# Macedonian, Norwegian, Persian (Farsi), Polish, Portuguese, Romanian, Russian, +# Serbian, Serbian-Cyrillic, Slovak, Slovene, Spanish, Swedish, Turkish, +# Ukrainian and Vietnamese. +# The default value is: English. + +OUTPUT_LANGUAGE = English + +# If the BRIEF_MEMBER_DESC tag is set to YES, doxygen will include brief member +# descriptions after the members that are listed in the file and class +# documentation (similar to Javadoc). Set to NO to disable this. +# The default value is: YES. + +BRIEF_MEMBER_DESC = YES + +# If the REPEAT_BRIEF tag is set to YES, doxygen will prepend the brief +# description of a member or function before the detailed description +# +# Note: If both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the +# brief descriptions will be completely suppressed. +# The default value is: YES. + +REPEAT_BRIEF = NO + +# This tag implements a quasi-intelligent brief description abbreviator that is +# used to form the text in various listings. Each string in this list, if found +# as the leading text of the brief description, will be stripped from the text +# and the result, after processing the whole list, is used as the annotated +# text. Otherwise, the brief description is used as-is. If left blank, the +# following values are used ($name is automatically replaced with the name of +# the entity):The $name class, The $name widget, The $name file, is, provides, +# specifies, contains, represents, a, an and the. + +ABBREVIATE_BRIEF = + +# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then +# doxygen will generate a detailed section even if there is only a brief +# description. +# The default value is: NO. + +ALWAYS_DETAILED_SEC = NO + +# If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all +# inherited members of a class in the documentation of that class as if those +# members were ordinary class members. Constructors, destructors and assignment +# operators of the base classes will not be shown. +# The default value is: NO. + +INLINE_INHERITED_MEMB = NO + +# If the FULL_PATH_NAMES tag is set to YES, doxygen will prepend the full path +# before files name in the file list and in the header files. If set to NO the +# shortest path that makes the file name unique will be used +# The default value is: YES. + +FULL_PATH_NAMES = NO + +# The STRIP_FROM_PATH tag can be used to strip a user-defined part of the path. +# Stripping is only done if one of the specified strings matches the left-hand +# part of the path. The tag can be used to show relative paths in the file list. +# If left blank the directory from which doxygen is run is used as the path to +# strip. +# +# Note that you can specify absolute paths here, but also relative paths, which +# will be relative from the directory where doxygen is started. +# This tag requires that the tag FULL_PATH_NAMES is set to YES. + +STRIP_FROM_PATH = + +# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of the +# path mentioned in the documentation of a class, which tells the reader which +# header file to include in order to use a class. If left blank only the name of +# the header file containing the class definition is used. Otherwise one should +# specify the list of include paths that are normally passed to the compiler +# using the -I flag. + +STRIP_FROM_INC_PATH = + +# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter (but +# less readable) file names. This can be useful is your file systems doesn't +# support long names like on DOS, Mac, or CD-ROM. +# The default value is: NO. + +SHORT_NAMES = NO + +# If the JAVADOC_AUTOBRIEF tag is set to YES then doxygen will interpret the +# first line (until the first dot) of a Javadoc-style comment as the brief +# description. If set to NO, the Javadoc-style will behave just like regular Qt- +# style comments (thus requiring an explicit @brief command for a brief +# description.) +# The default value is: NO. + +JAVADOC_AUTOBRIEF = NO + +# If the QT_AUTOBRIEF tag is set to YES then doxygen will interpret the first +# line (until the first dot) of a Qt-style comment as the brief description. If +# set to NO, the Qt-style will behave just like regular Qt-style comments (thus +# requiring an explicit \brief command for a brief description.) +# The default value is: NO. + +QT_AUTOBRIEF = NO + +# The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make doxygen treat a +# multi-line C++ special comment block (i.e. a block of //! or /// comments) as +# a brief description. This used to be the default behavior. The new default is +# to treat a multi-line C++ comment block as a detailed description. Set this +# tag to YES if you prefer the old behavior instead. +# +# Note that setting this tag to YES also means that rational rose comments are +# not recognized any more. +# The default value is: NO. + +MULTILINE_CPP_IS_BRIEF = NO + +# If the INHERIT_DOCS tag is set to YES then an undocumented member inherits the +# documentation from any documented member that it re-implements. +# The default value is: YES. + +INHERIT_DOCS = YES + +# If the SEPARATE_MEMBER_PAGES tag is set to YES then doxygen will produce a new +# page for each member. If set to NO, the documentation of a member will be part +# of the file/class/namespace that contains it. +# The default value is: NO. + +SEPARATE_MEMBER_PAGES = NO + +# The TAB_SIZE tag can be used to set the number of spaces in a tab. Doxygen +# uses this value to replace tabs by spaces in code fragments. +# Minimum value: 1, maximum value: 16, default value: 4. + +TAB_SIZE = 4 + +# This tag can be used to specify a number of aliases that act as commands in +# the documentation. An alias has the form: +# name=value +# For example adding +# "sideeffect=@par Side Effects:\n" +# will allow you to put the command \sideeffect (or @sideeffect) in the +# documentation, which will result in a user-defined paragraph with heading +# "Side Effects:". You can put \n's in the value part of an alias to insert +# newlines. + +ALIASES = + +# This tag can be used to specify a number of word-keyword mappings (TCL only). +# A mapping has the form "name=value". For example adding "class=itcl::class" +# will allow you to use the command class in the itcl::class meaning. + +TCL_SUBST = + +# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources +# only. Doxygen will then generate output that is more tailored for C. For +# instance, some of the names that are used will be different. The list of all +# members will be omitted, etc. +# The default value is: NO. + +OPTIMIZE_OUTPUT_FOR_C = YES + +# Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java or +# Python sources only. Doxygen will then generate output that is more tailored +# for that language. For instance, namespaces will be presented as packages, +# qualified scopes will look different, etc. +# The default value is: NO. + +OPTIMIZE_OUTPUT_JAVA = NO + +# Set the OPTIMIZE_FOR_FORTRAN tag to YES if your project consists of Fortran +# sources. Doxygen will then generate output that is tailored for Fortran. +# The default value is: NO. + +OPTIMIZE_FOR_FORTRAN = NO + +# Set the OPTIMIZE_OUTPUT_VHDL tag to YES if your project consists of VHDL +# sources. Doxygen will then generate output that is tailored for VHDL. +# The default value is: NO. + +OPTIMIZE_OUTPUT_VHDL = NO + +# Doxygen selects the parser to use depending on the extension of the files it +# parses. With this tag you can assign which parser to use for a given +# extension. Doxygen has a built-in mapping, but you can override or extend it +# using this tag. The format is ext=language, where ext is a file extension, and +# language is one of the parsers supported by doxygen: IDL, Java, Javascript, +# C#, C, C++, D, PHP, Objective-C, Python, Fortran (fixed format Fortran: +# FortranFixed, free formatted Fortran: FortranFree, unknown formatted Fortran: +# Fortran. In the later case the parser tries to guess whether the code is fixed +# or free formatted code, this is the default for Fortran type files), VHDL. For +# instance to make doxygen treat .inc files as Fortran files (default is PHP), +# and .f files as C (default is Fortran), use: inc=Fortran f=C. +# +# Note: For files without extension you can use no_extension as a placeholder. +# +# Note that for custom extensions you also need to set FILE_PATTERNS otherwise +# the files are not read by doxygen. + +EXTENSION_MAPPING = + +# If the MARKDOWN_SUPPORT tag is enabled then doxygen pre-processes all comments +# according to the Markdown format, which allows for more readable +# documentation. See http://daringfireball.net/projects/markdown/ for details. +# The output of markdown processing is further processed by doxygen, so you can +# mix doxygen, HTML, and XML commands with Markdown formatting. Disable only in +# case of backward compatibilities issues. +# The default value is: YES. + +MARKDOWN_SUPPORT = YES + +# When enabled doxygen tries to link words that correspond to documented +# classes, or namespaces to their corresponding documentation. Such a link can +# be prevented in individual cases by putting a % sign in front of the word or +# globally by setting AUTOLINK_SUPPORT to NO. +# The default value is: YES. + +AUTOLINK_SUPPORT = YES + +# If you use STL classes (i.e. std::string, std::vector, etc.) but do not want +# to include (a tag file for) the STL sources as input, then you should set this +# tag to YES in order to let doxygen match functions declarations and +# definitions whose arguments contain STL classes (e.g. func(std::string); +# versus func(std::string) {}). This also make the inheritance and collaboration +# diagrams that involve STL classes more complete and accurate. +# The default value is: NO. + +BUILTIN_STL_SUPPORT = YES + +# If you use Microsoft's C++/CLI language, you should set this option to YES to +# enable parsing support. +# The default value is: NO. + +CPP_CLI_SUPPORT = NO + +# Set the SIP_SUPPORT tag to YES if your project consists of sip (see: +# http://www.riverbankcomputing.co.uk/software/sip/intro) sources only. Doxygen +# will parse them like normal C++ but will assume all classes use public instead +# of private inheritance when no explicit protection keyword is present. +# The default value is: NO. + +SIP_SUPPORT = NO + +# For Microsoft's IDL there are propget and propput attributes to indicate +# getter and setter methods for a property. Setting this option to YES will make +# doxygen to replace the get and set methods by a property in the documentation. +# This will only work if the methods are indeed getting or setting a simple +# type. If this is not the case, or you want to show the methods anyway, you +# should set this option to NO. +# The default value is: YES. + +IDL_PROPERTY_SUPPORT = YES + +# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC +# tag is set to YES then doxygen will reuse the documentation of the first +# member in the group (if any) for the other members of the group. By default +# all members of a group must be documented explicitly. +# The default value is: NO. + +DISTRIBUTE_GROUP_DOC = NO + +# Set the SUBGROUPING tag to YES to allow class member groups of the same type +# (for instance a group of public functions) to be put as a subgroup of that +# type (e.g. under the Public Functions section). Set it to NO to prevent +# subgrouping. Alternatively, this can be done per class using the +# \nosubgrouping command. +# The default value is: YES. + +SUBGROUPING = YES + +# When the INLINE_GROUPED_CLASSES tag is set to YES, classes, structs and unions +# are shown inside the group in which they are included (e.g. using \ingroup) +# instead of on a separate page (for HTML and Man pages) or section (for LaTeX +# and RTF). +# +# Note that this feature does not work in combination with +# SEPARATE_MEMBER_PAGES. +# The default value is: NO. + +INLINE_GROUPED_CLASSES = NO + +# When the INLINE_SIMPLE_STRUCTS tag is set to YES, structs, classes, and unions +# with only public data fields or simple typedef fields will be shown inline in +# the documentation of the scope in which they are defined (i.e. file, +# namespace, or group documentation), provided this scope is documented. If set +# to NO, structs, classes, and unions are shown on a separate page (for HTML and +# Man pages) or section (for LaTeX and RTF). +# The default value is: NO. + +INLINE_SIMPLE_STRUCTS = YES + +# When TYPEDEF_HIDES_STRUCT tag is enabled, a typedef of a struct, union, or +# enum is documented as struct, union, or enum with the name of the typedef. So +# typedef struct TypeS {} TypeT, will appear in the documentation as a struct +# with name TypeT. When disabled the typedef will appear as a member of a file, +# namespace, or class. And the struct will be named TypeS. This can typically be +# useful for C code in case the coding convention dictates that all compound +# types are typedef'ed and only the typedef is referenced, never the tag name. +# The default value is: NO. + +TYPEDEF_HIDES_STRUCT = YES + +# The size of the symbol lookup cache can be set using LOOKUP_CACHE_SIZE. This +# cache is used to resolve symbols given their name and scope. Since this can be +# an expensive process and often the same symbol appears multiple times in the +# code, doxygen keeps a cache of pre-resolved symbols. If the cache is too small +# doxygen will become slower. If the cache is too large, memory is wasted. The +# cache size is given by this formula: 2^(16+LOOKUP_CACHE_SIZE). The valid range +# is 0..9, the default is 0, corresponding to a cache size of 2^16=65536 +# symbols. At the end of a run doxygen will report the cache usage and suggest +# the optimal cache size from a speed point of view. +# Minimum value: 0, maximum value: 9, default value: 0. + +LOOKUP_CACHE_SIZE = 0 + +#--------------------------------------------------------------------------- +# Build related configuration options +#--------------------------------------------------------------------------- + +# If the EXTRACT_ALL tag is set to YES, doxygen will assume all entities in +# documentation are documented, even if no documentation was available. Private +# class members and static file members will be hidden unless the +# EXTRACT_PRIVATE respectively EXTRACT_STATIC tags are set to YES. +# Note: This will also disable the warnings about undocumented members that are +# normally produced when WARNINGS is set to YES. +# The default value is: NO. + +EXTRACT_ALL = NO + +# If the EXTRACT_PRIVATE tag is set to YES, all private members of a class will +# be included in the documentation. +# The default value is: NO. + +EXTRACT_PRIVATE = NO + +# If the EXTRACT_PACKAGE tag is set to YES, all members with package or internal +# scope will be included in the documentation. +# The default value is: NO. + +EXTRACT_PACKAGE = NO + +# If the EXTRACT_STATIC tag is set to YES, all static members of a file will be +# included in the documentation. +# The default value is: NO. + +EXTRACT_STATIC = NO + +# If the EXTRACT_LOCAL_CLASSES tag is set to YES, classes (and structs) defined +# locally in source files will be included in the documentation. If set to NO, +# only classes defined in header files are included. Does not have any effect +# for Java sources. +# The default value is: YES. + +EXTRACT_LOCAL_CLASSES = NO + +# This flag is only useful for Objective-C code. If set to YES, local methods, +# which are defined in the implementation section but not in the interface are +# included in the documentation. If set to NO, only methods in the interface are +# included. +# The default value is: NO. + +EXTRACT_LOCAL_METHODS = NO + +# If this flag is set to YES, the members of anonymous namespaces will be +# extracted and appear in the documentation as a namespace called +# 'anonymous_namespace{file}', where file will be replaced with the base name of +# the file that contains the anonymous namespace. By default anonymous namespace +# are hidden. +# The default value is: NO. + +EXTRACT_ANON_NSPACES = NO + +# If the HIDE_UNDOC_MEMBERS tag is set to YES, doxygen will hide all +# undocumented members inside documented classes or files. If set to NO these +# members will be included in the various overviews, but no documentation +# section is generated. This option has no effect if EXTRACT_ALL is enabled. +# The default value is: NO. + +HIDE_UNDOC_MEMBERS = YES + +# If the HIDE_UNDOC_CLASSES tag is set to YES, doxygen will hide all +# undocumented classes that are normally visible in the class hierarchy. If set +# to NO, these classes will be included in the various overviews. This option +# has no effect if EXTRACT_ALL is enabled. +# The default value is: NO. + +HIDE_UNDOC_CLASSES = YES + +# If the HIDE_FRIEND_COMPOUNDS tag is set to YES, doxygen will hide all friend +# (class|struct|union) declarations. If set to NO, these declarations will be +# included in the documentation. +# The default value is: NO. + +HIDE_FRIEND_COMPOUNDS = NO + +# If the HIDE_IN_BODY_DOCS tag is set to YES, doxygen will hide any +# documentation blocks found inside the body of a function. If set to NO, these +# blocks will be appended to the function's detailed documentation block. +# The default value is: NO. + +HIDE_IN_BODY_DOCS = NO + +# The INTERNAL_DOCS tag determines if documentation that is typed after a +# \internal command is included. If the tag is set to NO then the documentation +# will be excluded. Set it to YES to include the internal documentation. +# The default value is: NO. + +INTERNAL_DOCS = NO + +# If the CASE_SENSE_NAMES tag is set to NO then doxygen will only generate file +# names in lower-case letters. If set to YES, upper-case letters are also +# allowed. This is useful if you have classes or files whose names only differ +# in case and if your file system supports case sensitive file names. Windows +# and Mac users are advised to set this option to NO. +# The default value is: system dependent. + +CASE_SENSE_NAMES = YES + +# If the HIDE_SCOPE_NAMES tag is set to NO then doxygen will show members with +# their full class and namespace scopes in the documentation. If set to YES, the +# scope will be hidden. +# The default value is: NO. + +HIDE_SCOPE_NAMES = NO + +# If the HIDE_COMPOUND_REFERENCE tag is set to NO (default) then doxygen will +# append additional text to a page's title, such as Class Reference. If set to +# YES the compound reference will be hidden. +# The default value is: NO. + +HIDE_COMPOUND_REFERENCE= NO + +# If the SHOW_INCLUDE_FILES tag is set to YES then doxygen will put a list of +# the files that are included by a file in the documentation of that file. +# The default value is: YES. + +SHOW_INCLUDE_FILES = YES + +# If the SHOW_GROUPED_MEMB_INC tag is set to YES then Doxygen will add for each +# grouped member an include statement to the documentation, telling the reader +# which file to include in order to use the member. +# The default value is: NO. + +SHOW_GROUPED_MEMB_INC = NO + +# If the FORCE_LOCAL_INCLUDES tag is set to YES then doxygen will list include +# files with double quotes in the documentation rather than with sharp brackets. +# The default value is: NO. + +FORCE_LOCAL_INCLUDES = NO + +# If the INLINE_INFO tag is set to YES then a tag [inline] is inserted in the +# documentation for inline members. +# The default value is: YES. + +INLINE_INFO = YES + +# If the SORT_MEMBER_DOCS tag is set to YES then doxygen will sort the +# (detailed) documentation of file and class members alphabetically by member +# name. If set to NO, the members will appear in declaration order. +# The default value is: YES. + +SORT_MEMBER_DOCS = NO + +# If the SORT_BRIEF_DOCS tag is set to YES then doxygen will sort the brief +# descriptions of file, namespace and class members alphabetically by member +# name. If set to NO, the members will appear in declaration order. Note that +# this will also influence the order of the classes in the class list. +# The default value is: NO. + +SORT_BRIEF_DOCS = NO + +# If the SORT_MEMBERS_CTORS_1ST tag is set to YES then doxygen will sort the +# (brief and detailed) documentation of class members so that constructors and +# destructors are listed first. If set to NO the constructors will appear in the +# respective orders defined by SORT_BRIEF_DOCS and SORT_MEMBER_DOCS. +# Note: If SORT_BRIEF_DOCS is set to NO this option is ignored for sorting brief +# member documentation. +# Note: If SORT_MEMBER_DOCS is set to NO this option is ignored for sorting +# detailed member documentation. +# The default value is: NO. + +SORT_MEMBERS_CTORS_1ST = NO + +# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the hierarchy +# of group names into alphabetical order. If set to NO the group names will +# appear in their defined order. +# The default value is: NO. + +SORT_GROUP_NAMES = NO + +# If the SORT_BY_SCOPE_NAME tag is set to YES, the class list will be sorted by +# fully-qualified names, including namespaces. If set to NO, the class list will +# be sorted only by class name, not including the namespace part. +# Note: This option is not very useful if HIDE_SCOPE_NAMES is set to YES. +# Note: This option applies only to the class list, not to the alphabetical +# list. +# The default value is: NO. + +SORT_BY_SCOPE_NAME = NO + +# If the STRICT_PROTO_MATCHING option is enabled and doxygen fails to do proper +# type resolution of all parameters of a function it will reject a match between +# the prototype and the implementation of a member function even if there is +# only one candidate or it is obvious which candidate to choose by doing a +# simple string match. By disabling STRICT_PROTO_MATCHING doxygen will still +# accept a match between prototype and implementation in such cases. +# The default value is: NO. + +STRICT_PROTO_MATCHING = NO + +# The GENERATE_TODOLIST tag can be used to enable (YES) or disable (NO) the todo +# list. This list is created by putting \todo commands in the documentation. +# The default value is: YES. + +GENERATE_TODOLIST = NO + +# The GENERATE_TESTLIST tag can be used to enable (YES) or disable (NO) the test +# list. This list is created by putting \test commands in the documentation. +# The default value is: YES. + +GENERATE_TESTLIST = NO + +# The GENERATE_BUGLIST tag can be used to enable (YES) or disable (NO) the bug +# list. This list is created by putting \bug commands in the documentation. +# The default value is: YES. + +GENERATE_BUGLIST = YES + +# The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or disable (NO) +# the deprecated list. This list is created by putting \deprecated commands in +# the documentation. +# The default value is: YES. + +GENERATE_DEPRECATEDLIST= YES + +# The ENABLED_SECTIONS tag can be used to enable conditional documentation +# sections, marked by \if ... \endif and \cond +# ... \endcond blocks. + +ENABLED_SECTIONS = + +# The MAX_INITIALIZER_LINES tag determines the maximum number of lines that the +# initial value of a variable or macro / define can have for it to appear in the +# documentation. If the initializer consists of more lines than specified here +# it will be hidden. Use a value of 0 to hide initializers completely. The +# appearance of the value of individual variables and macros / defines can be +# controlled using \showinitializer or \hideinitializer command in the +# documentation regardless of this setting. +# Minimum value: 0, maximum value: 10000, default value: 30. + +MAX_INITIALIZER_LINES = 30 + +# Set the SHOW_USED_FILES tag to NO to disable the list of files generated at +# the bottom of the documentation of classes and structs. If set to YES, the +# list will mention the files that were used to generate the documentation. +# The default value is: YES. + +SHOW_USED_FILES = YES + +# Set the SHOW_FILES tag to NO to disable the generation of the Files page. This +# will remove the Files entry from the Quick Index and from the Folder Tree View +# (if specified). +# The default value is: YES. + +SHOW_FILES = YES + +# Set the SHOW_NAMESPACES tag to NO to disable the generation of the Namespaces +# page. This will remove the Namespaces entry from the Quick Index and from the +# Folder Tree View (if specified). +# The default value is: YES. + +SHOW_NAMESPACES = YES + +# The FILE_VERSION_FILTER tag can be used to specify a program or script that +# doxygen should invoke to get the current version for each file (typically from +# the version control system). Doxygen will invoke the program by executing (via +# popen()) the command command input-file, where command is the value of the +# FILE_VERSION_FILTER tag, and input-file is the name of an input file provided +# by doxygen. Whatever the program writes to standard output is used as the file +# version. For an example see the documentation. + +FILE_VERSION_FILTER = + +# The LAYOUT_FILE tag can be used to specify a layout file which will be parsed +# by doxygen. The layout file controls the global structure of the generated +# output files in an output format independent way. To create the layout file +# that represents doxygen's defaults, run doxygen with the -l option. You can +# optionally specify a file name after the option, if omitted DoxygenLayout.xml +# will be used as the name of the layout file. +# +# Note that if you run doxygen from a directory containing a file called +# DoxygenLayout.xml, doxygen will parse it automatically even if the LAYOUT_FILE +# tag is left empty. + +LAYOUT_FILE = + +# The CITE_BIB_FILES tag can be used to specify one or more bib files containing +# the reference definitions. This must be a list of .bib files. The .bib +# extension is automatically appended if omitted. This requires the bibtex tool +# to be installed. See also http://en.wikipedia.org/wiki/BibTeX for more info. +# For LaTeX the style of the bibliography can be controlled using +# LATEX_BIB_STYLE. To use this feature you need bibtex and perl available in the +# search path. See also \cite for info how to create references. + +CITE_BIB_FILES = + +#--------------------------------------------------------------------------- +# Configuration options related to warning and progress messages +#--------------------------------------------------------------------------- + +# The QUIET tag can be used to turn on/off the messages that are generated to +# standard output by doxygen. If QUIET is set to YES this implies that the +# messages are off. +# The default value is: NO. + +QUIET = YES + +# The WARNINGS tag can be used to turn on/off the warning messages that are +# generated to standard error (stderr) by doxygen. If WARNINGS is set to YES +# this implies that the warnings are on. +# +# Tip: Turn warnings on while writing the documentation. +# The default value is: YES. + +WARNINGS = NO + +# If the WARN_IF_UNDOCUMENTED tag is set to YES then doxygen will generate +# warnings for undocumented members. If EXTRACT_ALL is set to YES then this flag +# will automatically be disabled. +# The default value is: YES. + +WARN_IF_UNDOCUMENTED = NO + +# If the WARN_IF_DOC_ERROR tag is set to YES, doxygen will generate warnings for +# potential errors in the documentation, such as not documenting some parameters +# in a documented function, or documenting parameters that don't exist or using +# markup commands wrongly. +# The default value is: YES. + +WARN_IF_DOC_ERROR = YES + +# This WARN_NO_PARAMDOC option can be enabled to get warnings for functions that +# are documented, but have no documentation for their parameters or return +# value. If set to NO, doxygen will only warn about wrong or incomplete +# parameter documentation, but not about the absence of documentation. +# The default value is: NO. + +WARN_NO_PARAMDOC = YES + +# The WARN_FORMAT tag determines the format of the warning messages that doxygen +# can produce. The string should contain the $file, $line, and $text tags, which +# will be replaced by the file and line number from which the warning originated +# and the warning text. Optionally the format may contain $version, which will +# be replaced by the version of the file (if it could be obtained via +# FILE_VERSION_FILTER) +# The default value is: $file:$line: $text. + +WARN_FORMAT = "$file:$line: $text" + +# The WARN_LOGFILE tag can be used to specify a file to which warning and error +# messages should be written. If left blank the output is written to standard +# error (stderr). + +WARN_LOGFILE = + +#--------------------------------------------------------------------------- +# Configuration options related to the input files +#--------------------------------------------------------------------------- + +# The INPUT tag is used to specify the files and/or directories that contain +# documented source files. You may enter file names like myfile.cpp or +# directories like /usr/src/myproject. Separate the files or directories with +# spaces. +# Note: If this tag is empty the current directory is searched. + +INPUT = ../../README.md ../input/chap2.md ../input/chap3.md ../../include ../../source ../../main ../../external_Pk ../input/mod.md + +# This tag can be used to specify the character encoding of the source files +# that doxygen parses. Internally doxygen uses the UTF-8 encoding. Doxygen uses +# libiconv (or the iconv built into libc) for the transcoding. See the libiconv +# documentation (see: http://www.gnu.org/software/libiconv) for the list of +# possible encodings. +# The default value is: UTF-8. + +INPUT_ENCODING = UTF-8 + +# If the value of the INPUT tag contains directories, you can use the +# FILE_PATTERNS tag to specify one or more wildcard patterns (like *.cpp and +# *.h) to filter out the source-files in the directories. If left blank the +# following patterns are tested:*.c, *.cc, *.cxx, *.cpp, *.c++, *.java, *.ii, +# *.ixx, *.ipp, *.i++, *.inl, *.idl, *.ddl, *.odl, *.h, *.hh, *.hxx, *.hpp, +# *.h++, *.cs, *.d, *.php, *.php4, *.php5, *.phtml, *.inc, *.m, *.markdown, +# *.md, *.mm, *.dox, *.py, *.f90, *.f, *.for, *.tcl, *.vhd, *.vhdl, *.ucf, +# *.qsf, *.as and *.js. + +FILE_PATTERNS = + +# The RECURSIVE tag can be used to specify whether or not subdirectories should +# be searched for input files as well. +# The default value is: NO. + +RECURSIVE = YES + +# The EXCLUDE tag can be used to specify files and/or directories that should be +# excluded from the INPUT source files. This way you can easily exclude a +# subdirectory from a directory tree whose root is specified with the INPUT tag. +# +# Note that relative paths are relative to the directory from which doxygen is +# run. + +EXCLUDE = ../../include/growTable.h + +# The EXCLUDE_SYMLINKS tag can be used to select whether or not files or +# directories that are symbolic links (a Unix file system feature) are excluded +# from the input. +# The default value is: NO. + +EXCLUDE_SYMLINKS = NO + +# If the value of the INPUT tag contains directories, you can use the +# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude +# certain files from those directories. +# +# Note that the wildcards are matched against the file with absolute path, so to +# exclude all test directories for example use the pattern */test/* + +EXCLUDE_PATTERNS = + +# The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names +# (namespaces, classes, functions, etc.) that should be excluded from the +# output. The symbol name can be a fully qualified name, a word, or if the +# wildcard * is used, a substring. Examples: ANamespace, AClass, +# AClass::ANamespace, ANamespace::*Test +# +# Note that the wildcards are matched against the file with absolute path, so to +# exclude all test directories use the pattern */test/* + +EXCLUDE_SYMBOLS = __ALLOCATE_PRECISION_PARAMETER__ + +# The EXAMPLE_PATH tag can be used to specify one or more files or directories +# that contain example code fragments that are included (see the \include +# command). + +EXAMPLE_PATH = + +# If the value of the EXAMPLE_PATH tag contains directories, you can use the +# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp and +# *.h) to filter out the source-files in the directories. If left blank all +# files are included. + +EXAMPLE_PATTERNS = + +# If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be +# searched for input files to be used with the \include or \dontinclude commands +# irrespective of the value of the RECURSIVE tag. +# The default value is: NO. + +EXAMPLE_RECURSIVE = NO + +# The IMAGE_PATH tag can be used to specify one or more files or directories +# that contain images that are to be included in the documentation (see the +# \image command). + +IMAGE_PATH = + +# The INPUT_FILTER tag can be used to specify a program that doxygen should +# invoke to filter for each input file. Doxygen will invoke the filter program +# by executing (via popen()) the command: +# +# +# +# where is the value of the INPUT_FILTER tag, and is the +# name of an input file. Doxygen will then use the output that the filter +# program writes to standard output. If FILTER_PATTERNS is specified, this tag +# will be ignored. +# +# Note that the filter must not add or remove lines; it is applied before the +# code is scanned, but not when the output code is generated. If lines are added +# or removed, the anchors will not be placed correctly. + +INPUT_FILTER = + +# The FILTER_PATTERNS tag can be used to specify filters on a per file pattern +# basis. Doxygen will compare the file name with each pattern and apply the +# filter if there is a match. The filters are a list of the form: pattern=filter +# (like *.cpp=my_cpp_filter). See INPUT_FILTER for further information on how +# filters are used. If the FILTER_PATTERNS tag is empty or if none of the +# patterns match the file name, INPUT_FILTER is applied. + +FILTER_PATTERNS = + +# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using +# INPUT_FILTER) will also be used to filter the input files that are used for +# producing the source files to browse (i.e. when SOURCE_BROWSER is set to YES). +# The default value is: NO. + +FILTER_SOURCE_FILES = NO + +# The FILTER_SOURCE_PATTERNS tag can be used to specify source filters per file +# pattern. A pattern will override the setting for FILTER_PATTERN (if any) and +# it is also possible to disable source filtering for a specific pattern using +# *.ext= (so without naming a filter). +# This tag requires that the tag FILTER_SOURCE_FILES is set to YES. + +FILTER_SOURCE_PATTERNS = + +# If the USE_MDFILE_AS_MAINPAGE tag refers to the name of a markdown file that +# is part of the input, its contents will be placed on the main page +# (index.html). This can be useful if you have a project on for instance GitHub +# and want to reuse the introduction page also for the doxygen output. + +USE_MDFILE_AS_MAINPAGE = + +#--------------------------------------------------------------------------- +# Configuration options related to source browsing +#--------------------------------------------------------------------------- + +# If the SOURCE_BROWSER tag is set to YES then a list of source files will be +# generated. Documented entities will be cross-referenced with these sources. +# +# Note: To get rid of all source code in the generated output, make sure that +# also VERBATIM_HEADERS is set to NO. +# The default value is: NO. + +SOURCE_BROWSER = NO + +# Setting the INLINE_SOURCES tag to YES will include the body of functions, +# classes and enums directly into the documentation. +# The default value is: NO. + +INLINE_SOURCES = NO + +# Setting the STRIP_CODE_COMMENTS tag to YES will instruct doxygen to hide any +# special comment blocks from generated source code fragments. Normal C, C++ and +# Fortran comments will always remain visible. +# The default value is: YES. + +STRIP_CODE_COMMENTS = YES + +# If the REFERENCED_BY_RELATION tag is set to YES then for each documented +# function all documented functions referencing it will be listed. +# The default value is: NO. + +REFERENCED_BY_RELATION = NO + +# If the REFERENCES_RELATION tag is set to YES then for each documented function +# all documented entities called/used by that function will be listed. +# The default value is: NO. + +REFERENCES_RELATION = NO + +# If the REFERENCES_LINK_SOURCE tag is set to YES and SOURCE_BROWSER tag is set +# to YES then the hyperlinks from functions in REFERENCES_RELATION and +# REFERENCED_BY_RELATION lists will link to the source code. Otherwise they will +# link to the documentation. +# The default value is: YES. + +REFERENCES_LINK_SOURCE = YES + +# If SOURCE_TOOLTIPS is enabled (the default) then hovering a hyperlink in the +# source code will show a tooltip with additional information such as prototype, +# brief description and links to the definition and documentation. Since this +# will make the HTML file larger and loading of large files a bit slower, you +# can opt to disable this feature. +# The default value is: YES. +# This tag requires that the tag SOURCE_BROWSER is set to YES. + +SOURCE_TOOLTIPS = YES + +# If the USE_HTAGS tag is set to YES then the references to source code will +# point to the HTML generated by the htags(1) tool instead of doxygen built-in +# source browser. The htags tool is part of GNU's global source tagging system +# (see http://www.gnu.org/software/global/global.html). You will need version +# 4.8.6 or higher. +# +# To use it do the following: +# - Install the latest version of global +# - Enable SOURCE_BROWSER and USE_HTAGS in the config file +# - Make sure the INPUT points to the root of the source tree +# - Run doxygen as normal +# +# Doxygen will invoke htags (and that will in turn invoke gtags), so these +# tools must be available from the command line (i.e. in the search path). +# +# The result: instead of the source browser generated by doxygen, the links to +# source code will now point to the output of htags. +# The default value is: NO. +# This tag requires that the tag SOURCE_BROWSER is set to YES. + +USE_HTAGS = NO + +# If the VERBATIM_HEADERS tag is set the YES then doxygen will generate a +# verbatim copy of the header file for each class for which an include is +# specified. Set to NO to disable this. +# See also: Section \class. +# The default value is: YES. + +VERBATIM_HEADERS = YES + +#--------------------------------------------------------------------------- +# Configuration options related to the alphabetical class index +#--------------------------------------------------------------------------- + +# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index of all +# compounds will be generated. Enable this if the project contains a lot of +# classes, structs, unions or interfaces. +# The default value is: YES. + +ALPHABETICAL_INDEX = NO + +# The COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns in +# which the alphabetical index list will be split. +# Minimum value: 1, maximum value: 20, default value: 5. +# This tag requires that the tag ALPHABETICAL_INDEX is set to YES. + +COLS_IN_ALPHA_INDEX = 5 + +# In case all classes in a project start with a common prefix, all classes will +# be put under the same header in the alphabetical index. The IGNORE_PREFIX tag +# can be used to specify a prefix (or a list of prefixes) that should be ignored +# while generating the index headers. +# This tag requires that the tag ALPHABETICAL_INDEX is set to YES. + +IGNORE_PREFIX = + +#--------------------------------------------------------------------------- +# Configuration options related to the HTML output +#--------------------------------------------------------------------------- + +# If the GENERATE_HTML tag is set to YES, doxygen will generate HTML output +# The default value is: YES. + +GENERATE_HTML = YES + +# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. If a +# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of +# it. +# The default directory is: html. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_OUTPUT = html + +# The HTML_FILE_EXTENSION tag can be used to specify the file extension for each +# generated HTML page (for example: .htm, .php, .asp). +# The default value is: .html. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_FILE_EXTENSION = .html + +# The HTML_HEADER tag can be used to specify a user-defined HTML header file for +# each generated HTML page. If the tag is left blank doxygen will generate a +# standard header. +# +# To get valid HTML the header file that includes any scripts and style sheets +# that doxygen needs, which is dependent on the configuration options used (e.g. +# the setting GENERATE_TREEVIEW). It is highly recommended to start with a +# default header using +# doxygen -w html new_header.html new_footer.html new_stylesheet.css +# YourConfigFile +# and then modify the file new_header.html. See also section "Doxygen usage" +# for information on how to generate the default header that doxygen normally +# uses. +# Note: The header is subject to change so you typically have to regenerate the +# default header when upgrading to a newer version of doxygen. For a description +# of the possible markers and block names see the documentation. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_HEADER = + +# The HTML_FOOTER tag can be used to specify a user-defined HTML footer for each +# generated HTML page. If the tag is left blank doxygen will generate a standard +# footer. See HTML_HEADER for more information on how to generate a default +# footer and what special commands can be used inside the footer. See also +# section "Doxygen usage" for information on how to generate the default footer +# that doxygen normally uses. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_FOOTER = + +# The HTML_STYLESHEET tag can be used to specify a user-defined cascading style +# sheet that is used by each HTML page. It can be used to fine-tune the look of +# the HTML output. If left blank doxygen will generate a default style sheet. +# See also section "Doxygen usage" for information on how to generate the style +# sheet that doxygen normally uses. +# Note: It is recommended to use HTML_EXTRA_STYLESHEET instead of this tag, as +# it is more robust and this tag (HTML_STYLESHEET) will in the future become +# obsolete. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_STYLESHEET = + +# The HTML_EXTRA_STYLESHEET tag can be used to specify additional user-defined +# cascading style sheets that are included after the standard style sheets +# created by doxygen. Using this option one can overrule certain style aspects. +# This is preferred over using HTML_STYLESHEET since it does not replace the +# standard style sheet and is therefore more robust against future updates. +# Doxygen will copy the style sheet files to the output directory. +# Note: The order of the extra style sheet files is of importance (e.g. the last +# style sheet in the list overrules the setting of the previous ones in the +# list). For an example see the documentation. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_EXTRA_STYLESHEET = + +# The HTML_EXTRA_FILES tag can be used to specify one or more extra images or +# other source files which should be copied to the HTML output directory. Note +# that these files will be copied to the base HTML output directory. Use the +# $relpath^ marker in the HTML_HEADER and/or HTML_FOOTER files to load these +# files. In the HTML_STYLESHEET file, use the file name only. Also note that the +# files will be copied as-is; there are no commands or markers available. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_EXTRA_FILES = + +# The HTML_COLORSTYLE_HUE tag controls the color of the HTML output. Doxygen +# will adjust the colors in the style sheet and background images according to +# this color. Hue is specified as an angle on a colorwheel, see +# http://en.wikipedia.org/wiki/Hue for more information. For instance the value +# 0 represents red, 60 is yellow, 120 is green, 180 is cyan, 240 is blue, 300 +# purple, and 360 is red again. +# Minimum value: 0, maximum value: 359, default value: 220. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_COLORSTYLE_HUE = 220 + +# The HTML_COLORSTYLE_SAT tag controls the purity (or saturation) of the colors +# in the HTML output. For a value of 0 the output will use grayscales only. A +# value of 255 will produce the most vivid colors. +# Minimum value: 0, maximum value: 255, default value: 100. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_COLORSTYLE_SAT = 220 + +# The HTML_COLORSTYLE_GAMMA tag controls the gamma correction applied to the +# luminance component of the colors in the HTML output. Values below 100 +# gradually make the output lighter, whereas values above 100 make the output +# darker. The value divided by 100 is the actual gamma applied, so 80 represents +# a gamma of 0.8, The value 220 represents a gamma of 2.2, and 100 does not +# change the gamma. +# Minimum value: 40, maximum value: 240, default value: 80. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_COLORSTYLE_GAMMA = 80 + +# If the HTML_TIMESTAMP tag is set to YES then the footer of each generated HTML +# page will contain the date and time when the page was generated. Setting this +# to NO can help when comparing the output of multiple runs. +# The default value is: YES. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_TIMESTAMP = YES + +# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML +# documentation will contain sections that can be hidden and shown after the +# page has loaded. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_DYNAMIC_SECTIONS = YES + +# With HTML_INDEX_NUM_ENTRIES one can control the preferred number of entries +# shown in the various tree structured indices initially; the user can expand +# and collapse entries dynamically later on. Doxygen will expand the tree to +# such a level that at most the specified number of entries are visible (unless +# a fully collapsed tree already exceeds this amount). So setting the number of +# entries 1 will produce a full collapsed tree by default. 0 is a special value +# representing an infinite number of entries and will result in a full expanded +# tree by default. +# Minimum value: 0, maximum value: 9999, default value: 100. +# This tag requires that the tag GENERATE_HTML is set to YES. + +HTML_INDEX_NUM_ENTRIES = 100 + +# If the GENERATE_DOCSET tag is set to YES, additional index files will be +# generated that can be used as input for Apple's Xcode 3 integrated development +# environment (see: http://developer.apple.com/tools/xcode/), introduced with +# OSX 10.5 (Leopard). To create a documentation set, doxygen will generate a +# Makefile in the HTML output directory. Running make will produce the docset in +# that directory and running make install will install the docset in +# ~/Library/Developer/Shared/Documentation/DocSets so that Xcode will find it at +# startup. See http://developer.apple.com/tools/creatingdocsetswithdoxygen.html +# for more information. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +GENERATE_DOCSET = NO + +# This tag determines the name of the docset feed. A documentation feed provides +# an umbrella under which multiple documentation sets from a single provider +# (such as a company or product suite) can be grouped. +# The default value is: Doxygen generated docs. +# This tag requires that the tag GENERATE_DOCSET is set to YES. + +DOCSET_FEEDNAME = "Doxygen generated docs" + +# This tag specifies a string that should uniquely identify the documentation +# set bundle. This should be a reverse domain-name style string, e.g. +# com.mycompany.MyDocSet. Doxygen will append .docset to the name. +# The default value is: org.doxygen.Project. +# This tag requires that the tag GENERATE_DOCSET is set to YES. + +DOCSET_BUNDLE_ID = org.doxygen.Project + +# The DOCSET_PUBLISHER_ID tag specifies a string that should uniquely identify +# the documentation publisher. This should be a reverse domain-name style +# string, e.g. com.mycompany.MyDocSet.documentation. +# The default value is: org.doxygen.Publisher. +# This tag requires that the tag GENERATE_DOCSET is set to YES. + +DOCSET_PUBLISHER_ID = org.doxygen.Publisher + +# The DOCSET_PUBLISHER_NAME tag identifies the documentation publisher. +# The default value is: Publisher. +# This tag requires that the tag GENERATE_DOCSET is set to YES. + +DOCSET_PUBLISHER_NAME = Publisher + +# If the GENERATE_HTMLHELP tag is set to YES then doxygen generates three +# additional HTML index files: index.hhp, index.hhc, and index.hhk. The +# index.hhp is a project file that can be read by Microsoft's HTML Help Workshop +# (see: http://www.microsoft.com/en-us/download/details.aspx?id=21138) on +# Windows. +# +# The HTML Help Workshop contains a compiler that can convert all HTML output +# generated by doxygen into a single compiled HTML file (.chm). Compiled HTML +# files are now used as the Windows 98 help format, and will replace the old +# Windows help format (.hlp) on all Windows platforms in the future. Compressed +# HTML files also contain an index, a table of contents, and you can search for +# words in the documentation. The HTML workshop also contains a viewer for +# compressed HTML files. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +GENERATE_HTMLHELP = NO + +# The CHM_FILE tag can be used to specify the file name of the resulting .chm +# file. You can add a path in front of the file if the result should not be +# written to the html output directory. +# This tag requires that the tag GENERATE_HTMLHELP is set to YES. + +CHM_FILE = + +# The HHC_LOCATION tag can be used to specify the location (absolute path +# including file name) of the HTML help compiler (hhc.exe). If non-empty, +# doxygen will try to run the HTML help compiler on the generated index.hhp. +# The file has to be specified with full path. +# This tag requires that the tag GENERATE_HTMLHELP is set to YES. + +HHC_LOCATION = + +# The GENERATE_CHI flag controls if a separate .chi index file is generated +# (YES) or that it should be included in the master .chm file (NO). +# The default value is: NO. +# This tag requires that the tag GENERATE_HTMLHELP is set to YES. + +GENERATE_CHI = NO + +# The CHM_INDEX_ENCODING is used to encode HtmlHelp index (hhk), content (hhc) +# and project file content. +# This tag requires that the tag GENERATE_HTMLHELP is set to YES. + +CHM_INDEX_ENCODING = + +# The BINARY_TOC flag controls whether a binary table of contents is generated +# (YES) or a normal table of contents (NO) in the .chm file. Furthermore it +# enables the Previous and Next buttons. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTMLHELP is set to YES. + +BINARY_TOC = NO + +# The TOC_EXPAND flag can be set to YES to add extra items for group members to +# the table of contents of the HTML help documentation and to the tree view. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTMLHELP is set to YES. + +TOC_EXPAND = NO + +# If the GENERATE_QHP tag is set to YES and both QHP_NAMESPACE and +# QHP_VIRTUAL_FOLDER are set, an additional index file will be generated that +# can be used as input for Qt's qhelpgenerator to generate a Qt Compressed Help +# (.qch) of the generated HTML documentation. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +GENERATE_QHP = NO + +# If the QHG_LOCATION tag is specified, the QCH_FILE tag can be used to specify +# the file name of the resulting .qch file. The path specified is relative to +# the HTML output folder. +# This tag requires that the tag GENERATE_QHP is set to YES. + +QCH_FILE = + +# The QHP_NAMESPACE tag specifies the namespace to use when generating Qt Help +# Project output. For more information please see Qt Help Project / Namespace +# (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#namespace). +# The default value is: org.doxygen.Project. +# This tag requires that the tag GENERATE_QHP is set to YES. + +QHP_NAMESPACE = org.doxygen.Project + +# The QHP_VIRTUAL_FOLDER tag specifies the namespace to use when generating Qt +# Help Project output. For more information please see Qt Help Project / Virtual +# Folders (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#virtual- +# folders). +# The default value is: doc. +# This tag requires that the tag GENERATE_QHP is set to YES. + +QHP_VIRTUAL_FOLDER = doc + +# If the QHP_CUST_FILTER_NAME tag is set, it specifies the name of a custom +# filter to add. For more information please see Qt Help Project / Custom +# Filters (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#custom- +# filters). +# This tag requires that the tag GENERATE_QHP is set to YES. + +QHP_CUST_FILTER_NAME = + +# The QHP_CUST_FILTER_ATTRS tag specifies the list of the attributes of the +# custom filter to add. For more information please see Qt Help Project / Custom +# Filters (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#custom- +# filters). +# This tag requires that the tag GENERATE_QHP is set to YES. + +QHP_CUST_FILTER_ATTRS = + +# The QHP_SECT_FILTER_ATTRS tag specifies the list of the attributes this +# project's filter section matches. Qt Help Project / Filter Attributes (see: +# http://qt-project.org/doc/qt-4.8/qthelpproject.html#filter-attributes). +# This tag requires that the tag GENERATE_QHP is set to YES. + +QHP_SECT_FILTER_ATTRS = + +# The QHG_LOCATION tag can be used to specify the location of Qt's +# qhelpgenerator. If non-empty doxygen will try to run qhelpgenerator on the +# generated .qhp file. +# This tag requires that the tag GENERATE_QHP is set to YES. + +QHG_LOCATION = + +# If the GENERATE_ECLIPSEHELP tag is set to YES, additional index files will be +# generated, together with the HTML files, they form an Eclipse help plugin. To +# install this plugin and make it available under the help contents menu in +# Eclipse, the contents of the directory containing the HTML and XML files needs +# to be copied into the plugins directory of eclipse. The name of the directory +# within the plugins directory should be the same as the ECLIPSE_DOC_ID value. +# After copying Eclipse needs to be restarted before the help appears. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +GENERATE_ECLIPSEHELP = NO + +# A unique identifier for the Eclipse help plugin. When installing the plugin +# the directory name containing the HTML and XML files should also have this +# name. Each documentation set should have its own identifier. +# The default value is: org.doxygen.Project. +# This tag requires that the tag GENERATE_ECLIPSEHELP is set to YES. + +ECLIPSE_DOC_ID = org.doxygen.Project + +# If you want full control over the layout of the generated HTML pages it might +# be necessary to disable the index and replace it with your own. The +# DISABLE_INDEX tag can be used to turn on/off the condensed index (tabs) at top +# of each HTML page. A value of NO enables the index and the value YES disables +# it. Since the tabs in the index contain the same information as the navigation +# tree, you can set this option to YES if you also set GENERATE_TREEVIEW to YES. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +DISABLE_INDEX = NO + +# The GENERATE_TREEVIEW tag is used to specify whether a tree-like index +# structure should be generated to display hierarchical information. If the tag +# value is set to YES, a side panel will be generated containing a tree-like +# index structure (just like the one that is generated for HTML Help). For this +# to work a browser that supports JavaScript, DHTML, CSS and frames is required +# (i.e. any modern browser). Windows users are probably better off using the +# HTML help feature. Via custom style sheets (see HTML_EXTRA_STYLESHEET) one can +# further fine-tune the look of the index. As an example, the default style +# sheet generated by doxygen has an example that shows how to put an image at +# the root of the tree instead of the PROJECT_NAME. Since the tree basically has +# the same information as the tab index, you could consider setting +# DISABLE_INDEX to YES when enabling this option. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +GENERATE_TREEVIEW = YES + +# The ENUM_VALUES_PER_LINE tag can be used to set the number of enum values that +# doxygen will group on one line in the generated HTML documentation. +# +# Note that a value of 0 will completely suppress the enum values from appearing +# in the overview section. +# Minimum value: 0, maximum value: 20, default value: 4. +# This tag requires that the tag GENERATE_HTML is set to YES. + +ENUM_VALUES_PER_LINE = 4 + +# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be used +# to set the initial width (in pixels) of the frame in which the tree is shown. +# Minimum value: 0, maximum value: 1500, default value: 250. +# This tag requires that the tag GENERATE_HTML is set to YES. + +TREEVIEW_WIDTH = 250 + +# If the EXT_LINKS_IN_WINDOW option is set to YES, doxygen will open links to +# external symbols imported via tag files in a separate window. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +EXT_LINKS_IN_WINDOW = NO + +# Use this tag to change the font size of LaTeX formulas included as images in +# the HTML documentation. When you change the font size after a successful +# doxygen run you need to manually remove any form_*.png images from the HTML +# output directory to force them to be regenerated. +# Minimum value: 8, maximum value: 50, default value: 10. +# This tag requires that the tag GENERATE_HTML is set to YES. + +FORMULA_FONTSIZE = 10 + +# Use the FORMULA_TRANPARENT tag to determine whether or not the images +# generated for formulas are transparent PNGs. Transparent PNGs are not +# supported properly for IE 6.0, but are supported on all modern browsers. +# +# Note that when changing this option you need to delete any form_*.png files in +# the HTML output directory before the changes have effect. +# The default value is: YES. +# This tag requires that the tag GENERATE_HTML is set to YES. + +FORMULA_TRANSPARENT = YES + +# Enable the USE_MATHJAX option to render LaTeX formulas using MathJax (see +# http://www.mathjax.org) which uses client side Javascript for the rendering +# instead of using pre-rendered bitmaps. Use this if you do not have LaTeX +# installed or if you want to formulas look prettier in the HTML output. When +# enabled you may also need to install MathJax separately and configure the path +# to it using the MATHJAX_RELPATH option. +# The default value is: NO. +# This tag requires that the tag GENERATE_HTML is set to YES. + +USE_MATHJAX = NO + +# When MathJax is enabled you can set the default output format to be used for +# the MathJax output. See the MathJax site (see: +# http://docs.mathjax.org/en/latest/output.html) for more details. +# Possible values are: HTML-CSS (which is slower, but has the best +# compatibility), NativeMML (i.e. MathML) and SVG. +# The default value is: HTML-CSS. +# This tag requires that the tag USE_MATHJAX is set to YES. + +MATHJAX_FORMAT = HTML-CSS + +# When MathJax is enabled you need to specify the location relative to the HTML +# output directory using the MATHJAX_RELPATH option. The destination directory +# should contain the MathJax.js script. For instance, if the mathjax directory +# is located at the same level as the HTML output directory, then +# MATHJAX_RELPATH should be ../mathjax. The default value points to the MathJax +# Content Delivery Network so you can quickly see the result without installing +# MathJax. However, it is strongly recommended to install a local copy of +# MathJax from http://www.mathjax.org before deployment. +# The default value is: http://cdn.mathjax.org/mathjax/latest. +# This tag requires that the tag USE_MATHJAX is set to YES. + +MATHJAX_RELPATH = http://cdn.mathjax.org/mathjax/latest + +# The MATHJAX_EXTENSIONS tag can be used to specify one or more MathJax +# extension names that should be enabled during MathJax rendering. For example +# MATHJAX_EXTENSIONS = TeX/AMSmath TeX/AMSsymbols +# This tag requires that the tag USE_MATHJAX is set to YES. + +MATHJAX_EXTENSIONS = + +# The MATHJAX_CODEFILE tag can be used to specify a file with javascript pieces +# of code that will be used on startup of the MathJax code. See the MathJax site +# (see: http://docs.mathjax.org/en/latest/output.html) for more details. For an +# example see the documentation. +# This tag requires that the tag USE_MATHJAX is set to YES. + +MATHJAX_CODEFILE = + +# When the SEARCHENGINE tag is enabled doxygen will generate a search box for +# the HTML output. The underlying search engine uses javascript and DHTML and +# should work on any modern browser. Note that when using HTML help +# (GENERATE_HTMLHELP), Qt help (GENERATE_QHP), or docsets (GENERATE_DOCSET) +# there is already a search function so this one should typically be disabled. +# For large projects the javascript based search engine can be slow, then +# enabling SERVER_BASED_SEARCH may provide a better solution. It is possible to +# search using the keyboard; to jump to the search box use + S +# (what the is depends on the OS and browser, but it is typically +# , /