mirror of
				https://github.com/KevinMidboe/linguist.git
				synced 2025-10-29 17:50:22 +00:00 
			
		
		
		
	fixing merge conflict
This commit is contained in:
		
							
								
								
									
										9
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										9
									
								
								.gitmodules
									
									
									
									
										vendored
									
									
								
							| @@ -818,6 +818,15 @@ | ||||
| [submodule "vendor/grammars/language-regexp"] | ||||
| 	path = vendor/grammars/language-regexp | ||||
| 	url = https://github.com/Alhadis/language-regexp | ||||
| [submodule "vendor/grammars/Terraform.tmLanguage"] | ||||
| 	path = vendor/grammars/Terraform.tmLanguage | ||||
| 	url = https://github.com/alexlouden/Terraform.tmLanguage | ||||
| [submodule "vendor/grammars/shaders-tmLanguage"] | ||||
| 	path = vendor/grammars/shaders-tmLanguage | ||||
| 	url = https://github.com/tgjones/shaders-tmLanguage | ||||
| [submodule "vendor/grammars/language-meson"] | ||||
| 	path = vendor/grammars/language-meson | ||||
| 	url = https://github.com/TingPing/language-meson | ||||
| [submodule "vendor/grammars/atom-language-p4"] | ||||
| 	path = vendor/grammars/atom-language-p4 | ||||
| 	url = https://github.com/TakeshiTseng/atom-language-p4 | ||||
|   | ||||
							
								
								
									
										2
									
								
								LICENSE
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								LICENSE
									
									
									
									
									
								
							| @@ -1,4 +1,4 @@ | ||||
| Copyright (c) 2011-2016 GitHub, Inc. | ||||
| Copyright (c) 2017 GitHub, Inc. | ||||
|  | ||||
| Permission is hereby granted, free of charge, to any person | ||||
| obtaining a copy of this software and associated documentation | ||||
|   | ||||
| @@ -16,7 +16,7 @@ Gem::Specification.new do |s| | ||||
|   s.add_dependency 'charlock_holmes', '~> 0.7.3' | ||||
|   s.add_dependency 'escape_utils',    '~> 1.1.0' | ||||
|   s.add_dependency 'mime-types',      '>= 1.19' | ||||
|   s.add_dependency 'rugged',          '0.25.1.1' | ||||
|   s.add_dependency 'rugged',          '>= 0.25.1' | ||||
|  | ||||
|   s.add_development_dependency 'minitest', '>= 5.0' | ||||
|   s.add_development_dependency 'mocha' | ||||
|   | ||||
| @@ -130,6 +130,8 @@ vendor/grammars/TLA: | ||||
| - source.tla | ||||
| vendor/grammars/TXL: | ||||
| - source.txl | ||||
| vendor/grammars/Terraform.tmLanguage: | ||||
| - source.terraform | ||||
| vendor/grammars/Textmate-Gosu-Bundle: | ||||
| - source.gosu.2 | ||||
| vendor/grammars/UrWeb-Language-Definition: | ||||
| @@ -408,6 +410,8 @@ vendor/grammars/language-less: | ||||
| - source.css.less | ||||
| vendor/grammars/language-maxscript: | ||||
| - source.maxscript | ||||
| vendor/grammars/language-meson: | ||||
| - source.meson | ||||
| vendor/grammars/language-ncl: | ||||
| - source.ncl | ||||
| vendor/grammars/language-ninja: | ||||
| @@ -573,6 +577,9 @@ vendor/grammars/scilab.tmbundle: | ||||
| - source.scilab | ||||
| vendor/grammars/secondlife-lsl: | ||||
| - source.lsl | ||||
| vendor/grammars/shaders-tmLanguage: | ||||
| - source.hlsl | ||||
| - source.shaderlab | ||||
| vendor/grammars/smali-sublime: | ||||
| - source.smali | ||||
| vendor/grammars/smalltalk-tmbundle: | ||||
|   | ||||
| @@ -95,7 +95,7 @@ module Linguist | ||||
|     # Returns sorted Array of result pairs. Each pair contains the | ||||
|     # String language name and a Float score. | ||||
|     def classify(tokens, languages) | ||||
|       return [] if tokens.nil? | ||||
|       return [] if tokens.nil? || languages.empty? | ||||
|       tokens = Tokenizer.tokenize(tokens) if tokens.is_a?(String) | ||||
|       scores = {} | ||||
|  | ||||
|   | ||||
| @@ -27,4 +27,4 @@ | ||||
| - (^|/)[Rr]eadme(\.|$) | ||||
|  | ||||
| # Samples folders | ||||
| - ^[Ss]amples/ | ||||
| - ^[Ss]amples?/ | ||||
|   | ||||
| @@ -465,5 +465,13 @@ module Linguist | ||||
|         Language["Scilab"] | ||||
|       end | ||||
|     end | ||||
|  | ||||
|     disambiguate ".tsx" do |data| | ||||
|       if /^\s*(import.+(from\s+|require\()['"]react|\/\/\/\s*<reference\s)/.match(data) | ||||
|         Language["TypeScript"] | ||||
|       elsif /^\s*<\?xml\s+version/i.match(data) | ||||
|         Language["XML"] | ||||
|       end | ||||
|     end | ||||
|   end | ||||
| end | ||||
|   | ||||
| @@ -1588,7 +1588,7 @@ HCL: | ||||
|   ace_mode: ruby | ||||
|   codemirror_mode: ruby | ||||
|   codemirror_mime_type: text/x-ruby | ||||
|   tm_scope: source.ruby | ||||
|   tm_scope: source.terraform | ||||
|   language_id: 144 | ||||
| HLSL: | ||||
|   type: programming | ||||
| @@ -1598,7 +1598,7 @@ HLSL: | ||||
|   - ".fxh" | ||||
|   - ".hlsli" | ||||
|   ace_mode: text | ||||
|   tm_scope: none | ||||
|   tm_scope: source.hlsl | ||||
|   language_id: 145 | ||||
| HTML: | ||||
|   type: markup | ||||
| @@ -2537,6 +2537,15 @@ Mercury: | ||||
|   - ".moo" | ||||
|   tm_scope: source.mercury | ||||
|   language_id: 229 | ||||
| Meson: | ||||
|   type: programming | ||||
|   color: "#007800" | ||||
|   filenames: | ||||
|   - meson.build | ||||
|   - meson_options.txt | ||||
|   tm_scope: source.meson | ||||
|   ace_mode: text | ||||
|   language_id: 799141244 | ||||
| Metal: | ||||
|   type: programming | ||||
|   color: "#8f14e9" | ||||
|   | ||||
| @@ -1,3 +1,3 @@ | ||||
| module Linguist | ||||
|   VERSION = "5.0.4" | ||||
|   VERSION = "5.0.5" | ||||
| end | ||||
|   | ||||
							
								
								
									
										135
									
								
								samples/HCL/main.tf
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										135
									
								
								samples/HCL/main.tf
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,135 @@ | ||||
| resource "aws_security_group" "elb_sec_group" { | ||||
|   description = "Allow traffic from the internet to ELB port 80" | ||||
|   vpc_id = "${var.vpc_id}" | ||||
|  | ||||
|   ingress { | ||||
|       from_port = 80 | ||||
|       to_port = 80 | ||||
|       protocol = "tcp" | ||||
|       cidr_blocks = ["${split(",", var.allowed_cidr_blocks)}"] | ||||
|   } | ||||
|  | ||||
|   egress { | ||||
|       from_port = 0 | ||||
|       to_port = 0 | ||||
|       protocol = "-1" | ||||
|       cidr_blocks = ["0.0.0.0/0"] | ||||
|   } | ||||
| } | ||||
|  | ||||
| resource "aws_security_group" "dokku_allow_ssh_from_internal" { | ||||
|   description = "Allow git access over ssh from the private subnet" | ||||
|   vpc_id = "${var.vpc_id}" | ||||
|  | ||||
|   ingress { | ||||
|       from_port = 22 | ||||
|       to_port = 22 | ||||
|       protocol = "tcp" | ||||
|       cidr_blocks = ["${var.private_subnet_cidr}"] | ||||
|   } | ||||
|  | ||||
|   egress { | ||||
|       from_port = 0 | ||||
|       to_port = 0 | ||||
|       protocol = "-1" | ||||
|       cidr_blocks = ["0.0.0.0/0"] | ||||
|   } | ||||
| } | ||||
|  | ||||
| resource "aws_security_group" "allow_from_elb_to_instance" { | ||||
|   description = "Allow traffic from the ELB to the private instance" | ||||
|   vpc_id = "${var.vpc_id}" | ||||
|  | ||||
|   ingress { | ||||
|       security_groups = ["${aws_security_group.elb_sec_group.id}"] | ||||
|       from_port = 80 | ||||
|       to_port = 80 | ||||
|       protocol = "tcp" | ||||
|   } | ||||
|  | ||||
|   egress { | ||||
|       from_port = 0 | ||||
|       to_port = 0 | ||||
|       protocol = "-1" | ||||
|       cidr_blocks = ["0.0.0.0/0"] | ||||
|   } | ||||
| } | ||||
|  | ||||
| resource "aws_instance" "dokku" { | ||||
|   ami = "ami-47a23a30" | ||||
|   instance_type = "${var.instance_type}" | ||||
|   associate_public_ip_address = false | ||||
|   key_name = "${var.key_name}" | ||||
|   subnet_id = "${var.private_subnet_id}" | ||||
|   vpc_security_group_ids = [ | ||||
|     "${var.bastion_sec_group_id}", | ||||
|     "${aws_security_group.allow_from_elb_to_instance.id}", | ||||
|     "${aws_security_group.dokku_allow_ssh_from_internal.id}" | ||||
|   ] | ||||
|   tags { | ||||
|     Name = "${var.name}" | ||||
|   } | ||||
|   connection { | ||||
|     user = "ubuntu" | ||||
|     private_key = "${var.private_key}" | ||||
|     bastion_host = "${var.bastion_host}" | ||||
|     bastion_port = "${var.bastion_port}" | ||||
|     bastion_user = "${var.bastion_user}" | ||||
|     bastion_private_key = "${var.bastion_private_key}" | ||||
|   } | ||||
|   provisioner "file" { | ||||
|     source = "${path.module}/../scripts/install-dokku.sh" | ||||
|     destination = "/home/ubuntu/install-dokku.sh" | ||||
|   } | ||||
|   provisioner "remote-exec" { | ||||
|     inline = [ | ||||
|       "chmod +x /home/ubuntu/install-dokku.sh", | ||||
|       "HOSTNAME=${var.hostname} /home/ubuntu/install-dokku.sh" | ||||
|     ] | ||||
|   } | ||||
| } | ||||
|  | ||||
| resource "aws_elb" "elb_dokku" { | ||||
|   name = "elb-dokku-${var.name}" | ||||
|   subnets = ["${var.public_subnet_id}"] | ||||
|   security_groups = ["${aws_security_group.elb_sec_group.id}"] | ||||
|  | ||||
|   listener { | ||||
|     instance_port = 80 | ||||
|     instance_protocol = "http" | ||||
|     lb_port = 80 | ||||
|     lb_protocol = "http" | ||||
|   } | ||||
|  | ||||
|   health_check { | ||||
|     healthy_threshold = 2 | ||||
|     unhealthy_threshold = 2 | ||||
|     timeout = 3 | ||||
|     target = "HTTP:80/" | ||||
|     interval = 30 | ||||
|   } | ||||
|  | ||||
|   instances = ["${aws_instance.dokku.id}"] | ||||
|   cross_zone_load_balancing = false | ||||
|   idle_timeout = 400 | ||||
|  | ||||
|   tags { | ||||
|     Name = "elb-dokku-${var.name}" | ||||
|   } | ||||
| } | ||||
|  | ||||
| resource "aws_route53_record" "dokku-deploy" { | ||||
|    zone_id = "${var.zone_id}" | ||||
|    name = "deploy.${var.hostname}" | ||||
|    type = "A" | ||||
|    ttl = "300" | ||||
|    records = ["${aws_instance.dokku.private_ip}"] | ||||
| } | ||||
|  | ||||
| resource "aws_route53_record" "dokku-wildcard" { | ||||
|    zone_id = "${var.zone_id}" | ||||
|    name = "*.${var.hostname}" | ||||
|    type = "CNAME" | ||||
|    ttl = "300" | ||||
|    records = ["${aws_elb.elb_dokku.dns_name}"] | ||||
| } | ||||
							
								
								
									
										51
									
								
								samples/Meson/filenames/meson.build
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										51
									
								
								samples/Meson/filenames/meson.build
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,51 @@ | ||||
| project('test', ['c'], | ||||
|   version: '0.1.0' | ||||
| ) | ||||
|  | ||||
| # This is a comment test('foo') | ||||
|  | ||||
| add_global_arguments(['-foo']) | ||||
| add_global_link_arguments(['-foo']) | ||||
|  | ||||
| gnome = import('gnome') # As is this | ||||
|  | ||||
| gnome.do_something('test') | ||||
|  | ||||
| meson.source_root() | ||||
|  | ||||
| foreach foo: bar | ||||
|   foreach baz : foo | ||||
|     message(baz) | ||||
|   endforeach | ||||
| endforeach | ||||
|  | ||||
| blah = ''' | ||||
| afjoakjflajf  # Test | ||||
| lflkasjf | ||||
| test\'test | ||||
| test\\\\test | ||||
| test\ntest | ||||
| ''' | ||||
|  | ||||
| foo = '' | ||||
| foo = '''''' | ||||
| foo = 'string' | ||||
| foo = '''string2''' | ||||
| foo = 12314 | ||||
| foo = 1231.1231 | ||||
| foo = true | ||||
| foo = false | ||||
| foo = ['te\'st', 1, 3.3, '''test'''] | ||||
| foo += 1231 | ||||
| foo = '@0@'.format('test') | ||||
| foo = include_directories('foo', kwarg: 'bar', include_directories: 'foo') | ||||
| foo = true ? 'true' : 'false' | ||||
| foo = 2 - 1 + 3 % 8 / 4 * 3 | ||||
|  | ||||
| if true and false | ||||
| elif false or true | ||||
| elif true not false | ||||
| elif foo == 12 | ||||
| elif (foo != 124) and (foo <= 200) | ||||
| else | ||||
| endif | ||||
							
								
								
									
										3
									
								
								samples/Meson/filenames/meson_options.txt
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										3
									
								
								samples/Meson/filenames/meson_options.txt
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,3 @@ | ||||
| option('with-something', type: 'boolean', | ||||
|   value: true, | ||||
| ) | ||||
							
								
								
									
										384
									
								
								samples/TypeScript/import.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										384
									
								
								samples/TypeScript/import.tsx
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,384 @@ | ||||
| // Fixture taken from https://github.com/graphcool/console/blob/dev/src/components/onboarding/PlaygroundCPopup/PlaygroundCPopup.tsx | ||||
|  | ||||
| import * as React from 'react' | ||||
| import {withRouter} from 'react-router' | ||||
| import {connect} from 'react-redux' | ||||
| import {bindActionCreators} from 'redux' | ||||
| import {nextStep, selectExample} from '../../../actions/gettingStarted' | ||||
| import {classnames} from '../../../utils/classnames' | ||||
| import Loading from '../../Loading/Loading' | ||||
| import {GettingStartedState} from '../../../types/gettingStarted' | ||||
| import {Example} from '../../../types/types' | ||||
| const classes: any = require('./PlaygroundCPopup.scss') | ||||
| import {$p} from 'graphcool-styles' | ||||
| import * as cx from 'classnames' | ||||
|  | ||||
| interface Tutorial { | ||||
|   title: string | ||||
|   description: string | ||||
|   image: string | ||||
|   link: string | ||||
| } | ||||
|  | ||||
| const guides: Tutorial[] = [ | ||||
|   { | ||||
|     title: 'Learnrelay.org', | ||||
|     description: 'A comprehensive, interactive introduction to Relay', | ||||
|     link: 'https://learnrelay.org/', | ||||
|     image: require('../../../assets/graphics/relay.png'), | ||||
|   }, | ||||
|   { | ||||
|     title: 'GraphQL and the amazing Apollo Client', | ||||
|     description: 'Explore an Application built using React and Angular 2', | ||||
|     link: 'https://medium.com/google-developer-experts/graphql-and-the-amazing-apollo-client-fe57e162a70c', | ||||
|     image: require('../../../assets/graphics/apollo.png'), | ||||
|   }, | ||||
|   { | ||||
|     title: 'Introducing Lokka', | ||||
|     description: 'A Simple JavaScript Client for GraphQL', | ||||
|     link: 'https://voice.kadira.io/introducing-lokka-a-simple-javascript-client-for-graphql-e0802695648c', | ||||
|     image: require('../../../assets/graphics/lokka.png'), | ||||
|   }, | ||||
| ] | ||||
|  | ||||
| const examples = { | ||||
|   ReactRelay: { | ||||
|     path: 'react-relay-instagram-example', | ||||
|     description: 'React + Relay', | ||||
|   }, | ||||
|   ReactApollo: { | ||||
|     path: 'react-apollo-instagram-example', | ||||
|     description: 'React + Apollo', | ||||
|   }, | ||||
|   ReactNativeApollo: { | ||||
|     path: 'react-native-apollo-instagram-example', | ||||
|     description: 'React Native + Apollo', | ||||
|   }, | ||||
|   AngularApollo: { | ||||
|     path: 'angular-apollo-instagram-example', | ||||
|     description: 'Angular + Apollo', | ||||
|   }, | ||||
| } | ||||
|  | ||||
| interface Props { | ||||
|   id: string | ||||
|   projectId: string | ||||
|   nextStep: () => Promise<void> | ||||
|   selectExample: (selectedExample: Example) => any | ||||
|   gettingStartedState: GettingStartedState | ||||
| } | ||||
|  | ||||
| interface State { | ||||
|   mouseOver: boolean | ||||
| } | ||||
|  | ||||
| class PlaygroundCPopup extends React.Component<Props, State> { | ||||
|  | ||||
|   state = { | ||||
|     mouseOver: false, | ||||
|   } | ||||
|  | ||||
|   refs: { | ||||
|     [key: string]: any | ||||
|     exampleAnchor: HTMLDivElement | ||||
|     congratsAnchor: HTMLDivElement | ||||
|     scroller: HTMLDivElement, | ||||
|   } | ||||
|  | ||||
|   componentDidUpdate(prevProps: Props, prevState: State) { | ||||
|     if (prevProps.gettingStartedState.selectedExample !== this.props.gettingStartedState.selectedExample) { | ||||
|       this.refs.scroller.scrollTop += this.refs.exampleAnchor.getBoundingClientRect().top | ||||
|     } | ||||
|  | ||||
|     if (prevProps.gettingStartedState.isCurrentStep('STEP5_WAITING') | ||||
|         && this.props.gettingStartedState.isCurrentStep('STEP5_DONE')) { | ||||
|       this.refs.scroller.scrollTop += this.refs.congratsAnchor.getBoundingClientRect().top | ||||
|  | ||||
|       const snd = new Audio(require('../../../assets/success.mp3') as string) | ||||
|       snd.volume = 0.5 | ||||
|       snd.play() | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   render() { | ||||
|     const {mouseOver} = this.state | ||||
|     const {selectedExample} = this.props.gettingStartedState | ||||
|     const hovering = !this.props.gettingStartedState.isCurrentStep('STEP4_CLICK_TEASER_STEP5') | ||||
|     const downloadUrl = (example) => `${__BACKEND_ADDR__}/resources/getting-started-example?repository=${examples[example].path}&project_id=${this.props.projectId}&user=graphcool-examples` // tslint:disable-line | ||||
|     return ( | ||||
|       <div | ||||
|         className='flex justify-center items-start w-100 h-100' | ||||
|         style={{ | ||||
|           transition: 'background-color 0.3s ease', | ||||
|           backgroundColor: hovering ? 'rgba(255,255,255,0.7)' : 'transparent', | ||||
|           width: 'calc(100% - 266px)', | ||||
|           pointerEvents: 'none', | ||||
|           overflow: 'hidden', | ||||
|         }} | ||||
|       > | ||||
|         <div | ||||
|           ref='scroller' | ||||
|           className='flex justify-center w-100' | ||||
|           style={{ | ||||
|             transition: 'height 0.5s ease', | ||||
|             height: hovering ? '100%' : mouseOver ? '190%' : '210%', | ||||
|             pointerEvents: hovering ? 'all' : 'none', | ||||
|             cursor: hovering ? 'auto' : 'pointer', | ||||
|             overflow: hovering ? 'auto' : 'hidden', | ||||
|             alignItems: selectedExample ? 'flex-start' : 'center', | ||||
|           }} | ||||
|         > | ||||
|           <div | ||||
|             className='bg-white br-2 shadow-2 mv-96' | ||||
|             style={{ | ||||
|               minWidth: 600, | ||||
|               maxWidth: 800, | ||||
|               pointerEvents: 'all', | ||||
|             }} | ||||
|             onMouseLeave={() => this.setState({ mouseOver: false })} | ||||
|             onMouseEnter={() => { | ||||
|               this.setState({ mouseOver: true }) | ||||
|             }} | ||||
|             onMouseOver={(e: any) => { | ||||
|               if (this.props.gettingStartedState.isCurrentStep('STEP4_CLICK_TEASER_STEP5')) { | ||||
|                 this.props.nextStep() | ||||
|               } | ||||
|             }} | ||||
|           > | ||||
|             <div className='ma-16 tc pb-25'> | ||||
|               <div className='fw3 ma-38 f-38'> | ||||
|                 You did it! Time to run an example. | ||||
|               </div> | ||||
|               <div className='fw2 f-16 mh-96 lh-1-4'> | ||||
|                 You have successfully set up your own Instagram backend.{' '} | ||||
|                 When building an app with Graphcool you can easily explore queries in the{' '} | ||||
|                 playground and "copy & paste" selected queries into your code.{' '} | ||||
|                 Of course, to do so, you need to implement the frontend first. | ||||
|               </div> | ||||
|               <div className='fw2 f-16 mh-96 lh-1-4 mt-16'> | ||||
|                 <div>We put together a simple app to show and add posts</div> | ||||
|                 <div>using the backend you just built, to test and run it locally.</div> | ||||
|               </div> | ||||
|             </div> | ||||
|             <div className='ma-16 tc pb-25'> | ||||
|               <div className='fw3 ma-38 f-25'> | ||||
|                 Select your preferred technology to download the example. | ||||
|               </div> | ||||
|               <div className='flex justify-between items-center w-100' ref='exampleAnchor'> | ||||
|                 <div | ||||
|                   className={classnames( | ||||
|                     classes.exampleButton, | ||||
|                     selectedExample === 'ReactRelay' ? classes.active : '', | ||||
|                   )} | ||||
|                   onClick={() => this.props.selectExample('ReactRelay')} | ||||
|                 > | ||||
|                   React + Relay | ||||
|                 </div> | ||||
|                 <div | ||||
|                   className={classnames( | ||||
|                     classes.exampleButton, | ||||
|                     selectedExample === 'ReactApollo' ? classes.active : '', | ||||
|                   )} | ||||
|                   onClick={() => this.props.selectExample('ReactApollo')} | ||||
|                 > | ||||
|                   React + Apollo | ||||
|                 </div> | ||||
|                 <div | ||||
|                   className={classnames( | ||||
|                     classes.exampleButton, | ||||
|                     selectedExample === 'ReactNativeApollo' ? classes.active : '', | ||||
|                   )} | ||||
|                   onClick={() => this.props.selectExample('ReactNativeApollo')} | ||||
|                 > | ||||
|                   React Native + Apollo | ||||
|                 </div> | ||||
|                 <div | ||||
|                   className={classnames( | ||||
|                     classes.exampleButton, | ||||
|                     selectedExample === 'AngularApollo' ? classes.active : '', | ||||
|                   )} | ||||
|                   onClick={() => this.props.selectExample('AngularApollo')} | ||||
|                 > | ||||
|                   Angular + Apollo | ||||
|                 </div> | ||||
|               </div> | ||||
|             </div> | ||||
|           {selectedExample && | ||||
|           <div> | ||||
|             <div className='w-100'> | ||||
|               <iframe | ||||
|                 className='w-100' | ||||
|                 height='480' | ||||
|                 allowFullScreen | ||||
|                 frameBorder='0' | ||||
|                 src={`https://www.youtube.com/embed/${this.getExampleVideoUrl(selectedExample)}`} | ||||
|               /> | ||||
|             </div> | ||||
|             <div | ||||
|               className='w-100 pa-25' | ||||
|               style={{ | ||||
|                 backgroundColor: '#FEF5D2', | ||||
|               }} | ||||
|             > | ||||
|               <div className='mt-25 mb-38 w-100 flex justify-center'> | ||||
|                 <a | ||||
|                   href={downloadUrl(selectedExample)} | ||||
|                   className='pa-16 white' | ||||
|                   style={{ | ||||
|                     backgroundColor: '#4A90E2', | ||||
|                   }} | ||||
|                 > | ||||
|                   Download example | ||||
|                 </a> | ||||
|               </div> | ||||
|               <div className='code dark-gray'> | ||||
|                 <div className='black-50'> | ||||
|                   # To see the example in action, run the following commands: | ||||
|                 </div> | ||||
|                 <div className='mv-16'> | ||||
|                   <div className='black'> | ||||
|                     npm install | ||||
|                   </div> | ||||
|                   <div className='black'> | ||||
|                     npm start | ||||
|                   </div> | ||||
|                 </div> | ||||
|                 <div className='black-50'> | ||||
|                   # You can now open the app on localhost:3000 | ||||
|                 </div> | ||||
|                 <div className='black-50'> | ||||
|                   # Please come back to this page once you're done. We're waiting here. 💤 | ||||
|                 </div> | ||||
|                 <div className={cx($p.w100, $p.flex, $p.flexRow, $p.justifyCenter, $p.mt25)}> | ||||
|                   <a href='#' onClick={ | ||||
|                     (e: any) => { | ||||
|                       e.preventDefault() | ||||
|                       // we need to skip the 'STEP5_WAITING' step | ||||
|                       this.props.nextStep() | ||||
|                       this.props.nextStep() | ||||
|                       this.props.nextStep() | ||||
|                     } | ||||
|                   }> | ||||
|                     Skip | ||||
|                   </a> | ||||
|                 </div> | ||||
|               </div> | ||||
|               {this.props.gettingStartedState.isCurrentStep('STEP5_WAITING') && | ||||
|               <div className='w-100 mv-96 flex justify-center'> | ||||
|                 <Loading /> | ||||
|               </div> | ||||
|               } | ||||
|             </div> | ||||
|           </div> | ||||
|           } | ||||
|         {this.props.gettingStartedState.isCurrentStep('STEP5_DONE') && | ||||
|           <div className='w-100 mb-96' ref='congratsAnchor'> | ||||
|             <div className='flex items-center flex-column pv-60 fw1'> | ||||
|               <div className='f-96'> | ||||
|                 🎉 | ||||
|               </div> | ||||
|               <div className='f-38 mt-38'> | ||||
|                 Congratulations! | ||||
|               </div> | ||||
|               <div className='f-38 mt-16'> | ||||
|                 We knew you had it in you. | ||||
|               </div> | ||||
|               <div className='f-16 mv-38'> | ||||
|                 Now go out there and build amazing things! | ||||
|               </div> | ||||
|             </div> | ||||
|             <div className='flex justify-between ph-25 pv-16'> | ||||
|               <div className='w-50 pr-16'> | ||||
|                 <div className='ttu ls-2 f-16 fw1 lh-1-4'> | ||||
|                   Get started on your own<br />with those excellent tutorials | ||||
|                 </div> | ||||
|                 <div className='mv-38'> | ||||
|                   {guides.map(guide => this.renderBox(guide))} | ||||
|                 </div> | ||||
|               </div> | ||||
|               <div className='w-50 pl-16'> | ||||
|                 <div className='ttu ls-2 f-16 fw1 lh-1-4'> | ||||
|                   Get more out of Graphcool<br />with our guides | ||||
|                 </div> | ||||
|                 <div className={`h-100 justify-start flex flex-column mv-38 ${classes.guides}`}> | ||||
|                   <a | ||||
|                     href='https://graph.cool/docs/tutorials/quickstart-2-daisheeb9x' | ||||
|                     className={`${classes.one} fw4 black db flex items-center mb-25`} | ||||
|                     target='_blank' | ||||
|                   > | ||||
|                     Declaring Relations | ||||
|                   </a> | ||||
|                   <a | ||||
|                     href='https://graph.cool/docs/tutorials/quickstart-3-saigai7cha' | ||||
|                     className={`${classes.two} fw4 black db flex items-center mb-25`} | ||||
|                     target='_blank' | ||||
|                   > | ||||
|                     Implementing Business Logic | ||||
|                   </a> | ||||
|                   <a | ||||
|                     href='https://graph.cool/docs/tutorials/thinking-in-terms-of-graphs-ahsoow1ool' | ||||
|                     target='_blank' | ||||
|                     className={`${classes.three} fw4 black db flex items-center mb-25`} | ||||
|                   > | ||||
|                     Thinking in terms of graphs | ||||
|                   </a> | ||||
|                 </div> | ||||
|               </div> | ||||
|             </div> | ||||
|             <div className='flex w-100 justify-center'> | ||||
|               <div | ||||
|                 className='f-25 mv-16 pv-16 ph-60 ls-1 ttu pointer bg-accent white dim' | ||||
|                 onClick={this.props.nextStep} | ||||
|               > | ||||
|                 Finish Onboarding | ||||
|               </div> | ||||
|             </div> | ||||
|           </div> | ||||
|           } | ||||
|           </div> | ||||
|         </div> | ||||
|       </div> | ||||
|     ) | ||||
|   } | ||||
|  | ||||
|   private renderBox = (tutorial: Tutorial) => { | ||||
|     return ( | ||||
|       <div key={tutorial.title} className='pa-16 mb-16 lh-1-4' style={{background: 'rgba(0,0,0,0.03)'}}> | ||||
|         <a className='flex items-center' href={tutorial.link} target='_blank'> | ||||
|           <div className='flex items-center justify-center' style={{ flex: '0 0 60px', height: 60 }}> | ||||
|             <img src={tutorial.image}/> | ||||
|           </div> | ||||
|           <div className='flex flex-column space-between ml-38'> | ||||
|             <div className='mb-6 dark-gray f-16'> | ||||
|               {tutorial.title} | ||||
|             </div> | ||||
|             <div className='fw1 mid-gray'> | ||||
|               {tutorial.description} | ||||
|             </div> | ||||
|           </div> | ||||
|         </a> | ||||
|       </div> | ||||
|     ) | ||||
|   } | ||||
|  | ||||
|   private getExampleVideoUrl = (example: Example): string => { | ||||
|     switch (example) { | ||||
|       case 'ReactRelay': return '_dj9Os2ev4M' | ||||
|       case 'ReactApollo': return '9nlwyPUPXjQ' | ||||
|       case 'ReactNativeApollo': return '9nlwyPUPXjQ' | ||||
|       case 'AngularApollo': return 'EzD5fJ-uniI' | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| const mapStateToProps = (state) => { | ||||
|   return { | ||||
|     gettingStartedState: state.gettingStarted.gettingStartedState, | ||||
|   } | ||||
| } | ||||
|  | ||||
| const mapDispatchToProps = (dispatch) => { | ||||
|   return bindActionCreators({nextStep, selectExample}, dispatch) | ||||
| } | ||||
|  | ||||
| export default connect(mapStateToProps, mapDispatchToProps)(withRouter(PlaygroundCPopup)) | ||||
							
								
								
									
										366
									
								
								samples/TypeScript/react-native.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										366
									
								
								samples/TypeScript/react-native.tsx
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,366 @@ | ||||
| // Fixture taken from https://github.com/bgrieder/RNTSExplorer/blob/master/typescript/components/TextExample.ios.tsx | ||||
|  | ||||
| /** | ||||
|  * The examples provided by Facebook are for non-commercial testing and | ||||
|  * evaluation purposes only. | ||||
|  * | ||||
|  * Facebook reserves all rights not expressly granted. | ||||
|  * | ||||
|  * 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 NON INFRINGEMENT. IN NO EVENT SHALL | ||||
|  * FACEBOOK 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. | ||||
|  * | ||||
|  * Typescript rewrite by Bruno Grieder | ||||
|  */ | ||||
|  | ||||
| 'use strict' | ||||
|  | ||||
| import * as React from 'react-native'; | ||||
| import RNTSExample from '../RNTSExample' | ||||
| import RNTSExampleModule from '../RNTSExampleModule' | ||||
|  | ||||
| const { | ||||
|           StyleSheet, | ||||
|           Text, | ||||
|           View, | ||||
|           } = React | ||||
|  | ||||
|  | ||||
| const styles = StyleSheet.create( | ||||
|     { | ||||
|         backgroundColorText: { | ||||
|             left:            5, | ||||
|             backgroundColor: 'rgba(100, 100, 100, 0.3)' | ||||
|         }, | ||||
|         entity:              { | ||||
|             fontWeight: '500', | ||||
|             color:      '#527fe4', | ||||
|         }, | ||||
|     } | ||||
| ) | ||||
|  | ||||
| class Entity extends React.Component<any,any> { | ||||
|     render() { | ||||
|         return ( | ||||
|             <Text style={styles.entity}> | ||||
|                 {this.props.children} | ||||
|             </Text> | ||||
|         ) | ||||
|     } | ||||
| } | ||||
|  | ||||
| interface AttrTogglerState { | ||||
|     fontWeight?: string | ||||
|     fontSize?: number | ||||
| } | ||||
|  | ||||
| class AttributeToggler extends React.Component<any, AttrTogglerState> { | ||||
|     componentWillMount() { | ||||
|         this.setState( | ||||
|             { | ||||
|                 fontWeight: '500', | ||||
|                 fontSize:   15 | ||||
|             } | ||||
|         ) | ||||
|     } | ||||
|  | ||||
|     private increaseSize = (): void => { | ||||
|         this.setState( { | ||||
|                            fontSize: this.state.fontSize + 1 | ||||
|                        } ) | ||||
|     } | ||||
|  | ||||
|     render() { | ||||
|         const curStyle: React.TextStyle = { fontSize: this.state.fontSize } | ||||
|         return ( | ||||
|             <Text> | ||||
|                 <Text style={curStyle}> | ||||
|                     Tap the controls below to change attributes. | ||||
|                 </Text> | ||||
|                 <Text> | ||||
|                     See how it will even work on{' '} | ||||
|                     <Text style={curStyle}> | ||||
|                         this nested text | ||||
|                     </Text> | ||||
|                     <Text onPress={this.increaseSize}> | ||||
|                         {'>> Increase Size <<'} | ||||
|                     </Text> | ||||
|                 </Text> | ||||
|             </Text> | ||||
|         ) | ||||
|     } | ||||
| } | ||||
|  | ||||
| export default { | ||||
|     title:       '<Text>', | ||||
|     description: 'Base component for rendering styled text.', | ||||
|     displayName: 'TextExample', | ||||
|     examples:    [ | ||||
|                      { | ||||
|                          title:  'Wrap', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <Text> | ||||
|                                      The text should wrap if it goes on multiple lines. See, this is going to | ||||
|                                      the next line. | ||||
|                                  </Text> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Padding', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <Text style={{padding: 10}}> | ||||
|                                      This text is indented by 10px padding on all sides. | ||||
|                                  </Text> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Font Family', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text style={{fontFamily: 'Cochin'}}> | ||||
|                                          Cochin | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontFamily: 'Cochin', fontWeight: 'bold'}}> | ||||
|                                          Cochin bold | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontFamily: 'Helvetica'}}> | ||||
|                                          Helvetica | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontFamily: 'Helvetica', fontWeight: 'bold'}}> | ||||
|                                          Helvetica bold | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontFamily: 'Verdana'}}> | ||||
|                                          Verdana | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontFamily: 'Verdana', fontWeight: 'bold'}}> | ||||
|                                          Verdana bold | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Font Size', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text style={{fontSize: 23}}> | ||||
|                                          Size 23 | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontSize: 8}}> | ||||
|                                          Size 8 | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Color', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text style={{color: 'red'}}> | ||||
|                                          Red color | ||||
|                                      </Text> | ||||
|                                      <Text style={{color: 'blue'}}> | ||||
|                                          Blue color | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Font Weight', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text style={{fontWeight: '100'}}> | ||||
|                                          Move fast and be ultralight | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontWeight: '200'}}> | ||||
|                                          Move fast and be light | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontWeight: 'normal'}}> | ||||
|                                          Move fast and be normal | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontWeight: 'bold'}}> | ||||
|                                          Move fast and be bold | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontWeight: '900'}}> | ||||
|                                          Move fast and be ultrabold | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Font Style', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text style={{fontStyle: 'normal'}}> | ||||
|                                          Normal text | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontStyle: 'italic'}}> | ||||
|                                          Italic text | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:       'Nested', | ||||
|                          description: 'Nested text components will inherit the styles of their ' + | ||||
|                                       'parents (only backgroundColor is inherited from non-Text parents).  ' + | ||||
|                                       '<Text> only supports other <Text> and raw text (strings) as children.', | ||||
|                          render:      function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text> | ||||
|                                          (Normal text, | ||||
|                                          <Text style={{fontWeight: 'bold'}}> | ||||
|                                              (and bold | ||||
|                                              <Text style={{fontSize: 11, color: '#527fe4'}}> | ||||
|                                                  (and tiny inherited bold blue) | ||||
|                                              </Text> | ||||
|                                              ) | ||||
|                                          </Text> | ||||
|                                          ) | ||||
|                                      </Text> | ||||
|                                      <Text style={{fontSize: 12}}> | ||||
|                                          <Entity>Entity Name</Entity> | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Text Align', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text style={{textAlign: 'left'}}> | ||||
|                                          left left left left left left left left left left left left left left left | ||||
|                                      </Text> | ||||
|                                      <Text style={{textAlign: 'center'}}> | ||||
|                                          center center center center center center center center center center center | ||||
|                                      </Text> | ||||
|                                      <Text style={{textAlign: 'right'}}> | ||||
|                                          right right right right right right right right right right right right right | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Spaces', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <Text> | ||||
|                                      A {'generated'} {' '} {'string'} and    some     spaces | ||||
|                                  </Text> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Line Height', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <Text> | ||||
|                                      <Text style={{lineHeight: 35}}> | ||||
|                                          A lot of space between the lines of this long passage that should | ||||
|                                          wrap once. | ||||
|                                      </Text> | ||||
|                                  </Text> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:       'Empty Text', | ||||
|                          description: 'It\'s ok to have Text with zero or null children.', | ||||
|                          render:      function () { | ||||
|                              return ( | ||||
|                                  <Text /> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'Toggling Attributes', | ||||
|                          render: (): React.ReactElement<any> => { | ||||
|                              return <AttributeToggler /> | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:       'backgroundColor attribute', | ||||
|                          description: 'backgroundColor is inherited from all types of views.', | ||||
|                          render:      function () { | ||||
|                              return ( | ||||
|                                  <View style={{backgroundColor: 'yellow'}}> | ||||
|                                      <Text> | ||||
|                                          Yellow background inherited from View parent, | ||||
|                                          <Text style={{backgroundColor: '#ffaaaa'}}> | ||||
|                                              {' '}red background, | ||||
|                                              <Text style={{backgroundColor: '#aaaaff'}}> | ||||
|                                                  {' '}blue background, | ||||
|                                                  <Text> | ||||
|                                                      {' '}inherited blue background, | ||||
|                                                      <Text style={{backgroundColor: '#aaffaa'}}> | ||||
|                                                          {' '}nested green background. | ||||
|                                                      </Text> | ||||
|                                                  </Text> | ||||
|                                              </Text> | ||||
|                                          </Text> | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'containerBackgroundColor attribute', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <View style={{flexDirection: 'row', height: 85}}> | ||||
|                                          <View style={{backgroundColor: '#ffaaaa', width: 150}}/> | ||||
|                                          <View style={{backgroundColor: '#aaaaff', width: 150}}/> | ||||
|                                      </View> | ||||
|                                      <Text style={[styles.backgroundColorText, {top: -80}]}> | ||||
|                                          Default containerBackgroundColor (inherited) + backgroundColor wash | ||||
|                                      </Text> | ||||
|                                      <Text style={[ | ||||
|                                             styles.backgroundColorText, | ||||
|                                             {top: -70, containerBackgroundColor: 'transparent'} | ||||
|                                         ]}> | ||||
|                                          {"containerBackgroundColor: 'transparent' + backgroundColor wash"} | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          }, | ||||
|                      }, | ||||
|                      { | ||||
|                          title:  'numberOfLines attribute', | ||||
|                          render: function () { | ||||
|                              return ( | ||||
|                                  <View> | ||||
|                                      <Text numberOfLines={1}> | ||||
|                                          Maximum of one line no matter now much I write here. If I keep writing it{"'"}ll just truncate after one line | ||||
|                                      </Text> | ||||
|                                      <Text numberOfLines={2} style={{marginTop: 20}}> | ||||
|                                          Maximum of two lines no matter now much I write here. If I keep writing it{"'"}ll just truncate after two lines | ||||
|                                      </Text> | ||||
|                                      <Text style={{marginTop: 20}}> | ||||
|                                          No maximum lines specified no matter now much I write here. If I keep writing it{"'"}ll just keep going and going | ||||
|                                      </Text> | ||||
|                                  </View> | ||||
|                              ) | ||||
|                          } | ||||
|                      } ] as RNTSExample[] | ||||
| } as RNTSExampleModule | ||||
							
								
								
									
										240
									
								
								samples/TypeScript/require.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										240
									
								
								samples/TypeScript/require.tsx
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,240 @@ | ||||
| // Fixture taken from https://github.com/jcingroup/C551608_Roki/blob/master/Work.WebProj/Scripts/src/tsx/m-parm.tsx | ||||
|  | ||||
| import $ = require('jquery'); | ||||
| import React = require('react'); | ||||
| import ReactDOM = require('react-dom'); | ||||
| import Moment = require('moment'); | ||||
| import ReactBootstrap = require("react-bootstrap"); | ||||
| import CommCmpt = require('comm-cmpt'); | ||||
| import CommFunc = require('comm-func'); | ||||
|  | ||||
| namespace Parm { | ||||
|     interface ParamData { | ||||
|         Email?: string; | ||||
|         PurchaseTotal?: number; | ||||
|         HomoiothermyFee?: number; | ||||
|         RefrigerFee?: number; | ||||
|         AccountName?: string; | ||||
|         BankName?: string; | ||||
|         BankCode?: string; | ||||
|         AccountNumber?: string; | ||||
|         Fee?: number; | ||||
|     } | ||||
|     export class GridForm extends React.Component<any, { param?: ParamData }>{ | ||||
|  | ||||
|  | ||||
|         constructor() { | ||||
|  | ||||
|             super(); | ||||
|             this.queryInitData = this.queryInitData.bind(this); | ||||
|             this.handleSubmit = this.handleSubmit.bind(this); | ||||
|             this.componentDidMount = this.componentDidMount.bind(this); | ||||
|             this.setInputValue = this.setInputValue.bind(this); | ||||
|             this.render = this.render.bind(this); | ||||
|             this.state = { | ||||
|                 param: { | ||||
|                     Email: null, | ||||
|                     PurchaseTotal: 0, | ||||
|                     HomoiothermyFee: 0, | ||||
|                     RefrigerFee:0, | ||||
|                     AccountName: null, | ||||
|                     BankName: null, | ||||
|                     BankCode: null, | ||||
|                     AccountNumber: null, | ||||
|                     Fee: 0 | ||||
|                 } | ||||
|             } | ||||
|         } | ||||
|         static defaultProps = { | ||||
|             apiInitPath: gb_approot + 'Active/ParmData/aj_ParamInit', | ||||
|             apiPath: gb_approot + 'api/GetAction/PostParamData' | ||||
|         } | ||||
|         componentDidMount() { | ||||
|             this.queryInitData(); | ||||
|         } | ||||
|         queryInitData() { | ||||
|             CommFunc.jqGet(this.props.apiInitPath, {}) | ||||
|                 .done((data, textStatus, jqXHRdata) => { | ||||
|                     this.setState({ param: data }); | ||||
|                 }) | ||||
|                 .fail((jqXHR, textStatus, errorThrown) => { | ||||
|                     CommFunc.showAjaxError(errorThrown); | ||||
|                 }); | ||||
|         } | ||||
|         handleSubmit(e: React.FormEvent) { | ||||
|  | ||||
|             e.preventDefault(); | ||||
|             CommFunc.jqPost(this.props.apiPath, this.state.param) | ||||
|                 .done((data, textStatus, jqXHRdata) => { | ||||
|                     if (data.result) { | ||||
|                         CommFunc.tosMessage(null, '修改完成', 1); | ||||
|                     } else { | ||||
|                         alert(data.message); | ||||
|                     } | ||||
|                 }) | ||||
|                 .fail((jqXHR, textStatus, errorThrown) => { | ||||
|                     CommFunc.showAjaxError(errorThrown); | ||||
|                 }); | ||||
|             return; | ||||
|         } | ||||
|         handleOnBlur(date) { | ||||
|  | ||||
|         } | ||||
|         setInputValue(name: string, e: React.SyntheticEvent) { | ||||
|             let input: HTMLInputElement = e.target as HTMLInputElement; | ||||
|             let obj = this.state.param; | ||||
|             obj[name] = input.value; | ||||
|             this.setState({ param: obj }); | ||||
|         } | ||||
|         render() { | ||||
|  | ||||
|             var outHtml: JSX.Element = null; | ||||
|  | ||||
|             let param = this.state.param; | ||||
|             let InputDate = CommCmpt.InputDate; | ||||
|  | ||||
|             outHtml = ( | ||||
|                 <div> | ||||
|     <ul className="breadcrumb"> | ||||
|         <li><i className="fa-list-alt"></i> | ||||
|             {this.props.menuName} | ||||
|             </li> | ||||
|         </ul> | ||||
|     <h4 className="title"> {this.props.caption} 基本資料維護</h4> | ||||
|     <form className="form-horizontal" onSubmit={this.handleSubmit}> | ||||
|         <div className="col-xs-12"> | ||||
|             <div className="item-box"> | ||||
|                 {/*--email--*/} | ||||
|                 <div className="item-title text-center"> | ||||
|                 <h5>Email信箱設定</h5> | ||||
|                     </div> | ||||
|                     <div className="alert alert-warning" role="alert"> | ||||
|                         <ol> | ||||
|                             <li>多筆信箱請用「<strong className="text-danger">, </strong>」逗號分開。<br />ex.<strong>user1 @demo.com.tw, user2 @demo.com.tw</strong></li> | ||||
|                             <li>Email 前面可填收件人姓名,用「<strong className="text-danger">: </strong>」冒號分隔姓名和信箱,此項非必要,可省略。<br />ex.<strong>收件人A: user1 @demo.com.tw, 收件人B: user2 @demo.com.tw</strong></li> | ||||
|                             </ol> | ||||
|                         </div> | ||||
|                     <div className="form-group"> | ||||
|                        <label className="col-xs-1 control-label">收件信箱</label> | ||||
|                        <div className="col-xs-9"> | ||||
|                                 <input className="form-control" type="text" | ||||
|                                     value={param.Email} | ||||
|                                     onChange={this.setInputValue.bind(this, 'Email') } | ||||
|                                     maxLength={500} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         </div> | ||||
|                 {/*--email end--*/} | ||||
|                 {/*--shoppingCost--*/} | ||||
|                 <div className="item-title text-center"> | ||||
|                 <h5>訂單運費設定</h5> | ||||
|                     </div> | ||||
|                     <div className="form-group"> | ||||
|                        <label className="col-xs-3 control-label">會員下訂單,當訂單金額少於NT$</label> | ||||
|                        <div className="col-xs-1"> | ||||
|                                 <input className="form-control" type="number" | ||||
|                                     value={param.PurchaseTotal} | ||||
|                                     onChange={this.setInputValue.bind(this, 'PurchaseTotal') } | ||||
|                                     min={0} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         <label className="col-xs-2 control-label">元時須付常溫運費NT$</label> | ||||
|                        <div className="col-xs-1"> | ||||
|                                 <input className="form-control" type="number" | ||||
|                                     value={param.HomoiothermyFee} | ||||
|                                     onChange={this.setInputValue.bind(this, 'HomoiothermyFee') } | ||||
|                                     min={0} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         <label className="col-xs-2 control-label">元或冷凍(冷藏)運費NT$</label> | ||||
|                        <div className="col-xs-1"> | ||||
|                                 <input className="form-control" type="number" | ||||
|                                     value={param.RefrigerFee} | ||||
|                                     onChange={this.setInputValue.bind(this, 'RefrigerFee') } | ||||
|                                     min={0} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         <label className="col-xs-1 control-label">元</label> | ||||
|                         </div> | ||||
|  | ||||
|                 {/*--shoppingCost end--*/} | ||||
|                 {/*--Payment--*/} | ||||
|                 <div className="item-title text-center"> | ||||
|                 <h5>付款方式</h5> | ||||
|                     </div> | ||||
|                     <div className="form-group"> | ||||
|                      <label className="col-xs-4 control-label">當付款方式選擇『ATM轉帳』時,銀行帳號資料為: </label> | ||||
|                         </div> | ||||
|                     <div className="form-group"> | ||||
|                        <label className="col-xs-2 control-label">戶名: </label> | ||||
|                        <div className="col-xs-3"> | ||||
|                                 <input className="form-control" type="text" | ||||
|                                     value={param.AccountName} | ||||
|                                     onChange={this.setInputValue.bind(this, 'AccountName') } | ||||
|                                     maxLength={16} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         </div> | ||||
|                     <div className="form-group"> | ||||
|                        <label className="col-xs-2 control-label">銀行: </label> | ||||
|                        <div className="col-xs-3"> | ||||
|                                 <input className="form-control" type="text" | ||||
|                                     value={param.BankName} | ||||
|                                     onChange={this.setInputValue.bind(this, 'BankName') } | ||||
|                                     maxLength={16} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         </div> | ||||
|                     <div className="form-group"> | ||||
|                        <label className="col-xs-2 control-label">代碼: </label> | ||||
|                        <div className="col-xs-3"> | ||||
|                                 <input className="form-control" type="text" | ||||
|                                     value={param.BankCode} | ||||
|                                     onChange={this.setInputValue.bind(this, 'BankCode') } | ||||
|                                     maxLength={5} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         </div> | ||||
|                     <div className="form-group"> | ||||
|                        <label className="col-xs-2 control-label">帳號: </label> | ||||
|                        <div className="col-xs-3"> | ||||
|                                 <input className="form-control" type="text" | ||||
|                                     value={param.AccountNumber} | ||||
|                                     onChange={this.setInputValue.bind(this, 'AccountNumber') } | ||||
|                                     maxLength={16} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                         </div> | ||||
|                     {/*<div className="form-group"> | ||||
|                      <label className="col-xs-4 control-label">當付款方式選擇『貨到付款』時,須加NT$ </label> | ||||
|                        <div className="col-xs-1"> | ||||
|                                 <input className="form-control" type="number" | ||||
|                                     value={param.Fee} | ||||
|                                     onChange={this.setInputValue.bind(this, 'Fee') } | ||||
|                                     min={0} | ||||
|                                     required/> | ||||
|                            </div> | ||||
|                      <label className="control-label">元手續費</label> | ||||
|                         </div>*/} | ||||
|                 {/*--Payment end--*/} | ||||
|                 </div> | ||||
|  | ||||
|  | ||||
|  | ||||
|             <div className="form-action"> | ||||
|                 <div className="col-xs-4 col-xs-offset-5"> | ||||
|                     <button type="submit" className="btn-primary"><i className="fa-check"></i> 儲存</button> | ||||
|                     </div> | ||||
|                 </div> | ||||
|             </div> | ||||
|         </form> | ||||
|                     </div> | ||||
|             ); | ||||
|  | ||||
|             return outHtml; | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  | ||||
| var dom = document.getElementById('page_content'); | ||||
| ReactDOM.render(<Parm.GridForm caption={gb_caption} menuName={gb_menuname} iconClass="fa-list-alt" />, dom); | ||||
							
								
								
									
										863
									
								
								samples/TypeScript/triple-slash-reference.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										863
									
								
								samples/TypeScript/triple-slash-reference.tsx
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,863 @@ | ||||
| /// <reference path="../DefinitelyTyped/react/react-global.d.ts" /> | ||||
|  | ||||
| // Fixture taken from https://github.com/RyanCavanaugh/koany/blob/master/koany.tsx | ||||
|  | ||||
| interface Garden { | ||||
| 	colors: Gardens.RockColor[]; | ||||
| 	shapes: Gardens.RockShape[]; | ||||
| } | ||||
|  | ||||
| namespace Gardens { | ||||
| 	export enum RockShape { | ||||
| 		Empty, | ||||
| 		Circle, | ||||
| 		Triangle, | ||||
| 		Square, | ||||
| 		Max | ||||
| 	} | ||||
| 	export const RockShapes = [RockShape.Circle, RockShape.Triangle, RockShape.Square]; | ||||
| 	export const RockShapesAndEmpty = RockShapes.concat(RockShape.Empty); | ||||
|  | ||||
| 	export enum RockColor { | ||||
| 		Empty, | ||||
| 		White, | ||||
| 		Red, | ||||
| 		Black, | ||||
| 		Max | ||||
| 	} | ||||
| 	export const RockColors = [RockColor.White, RockColor.Red, RockColor.Black]; | ||||
| 	export const RockColorsAndEmpty = RockColors.concat(RockColor.Empty); | ||||
|  | ||||
| 	export const Size = 9; | ||||
|  | ||||
| 	// 012 | ||||
| 	// 345 | ||||
| 	// 678 | ||||
| 	export const adjacencies = [ | ||||
| 		[1, 3], [0, 4, 2], [1, 5], | ||||
| 		[0, 4, 6], [3, 1, 7, 5], [2, 4, 8], | ||||
| 		[3, 7], [6, 4, 8], [7, 5] | ||||
| 	]; | ||||
| } | ||||
|  | ||||
| module Koan { | ||||
| 	export enum DescribeContext { | ||||
| 		// every "white stone" is ... | ||||
| 		Singular, | ||||
| 		// all "white stones" are | ||||
| 		Plural, | ||||
| 		// every stone in the top row is "white" | ||||
| 		Adjectival | ||||
| 	} | ||||
|  | ||||
| 	export enum PartType { | ||||
| 		Selector, | ||||
| 		Aspect | ||||
| 	} | ||||
|  | ||||
| 	export enum StateTestResult { | ||||
| 		Fail = 0, | ||||
| 		WeakPass = 1, | ||||
| 		Pass = 2 | ||||
| 	} | ||||
|  | ||||
| 	/// A general format for producing a Statement | ||||
| 	export interface StatementTemplate<T> { | ||||
| 		holes: PartType[]; | ||||
| 		describe(args: T): string; | ||||
| 		test(g: Garden, args: T): StateTestResult; | ||||
| 	} | ||||
|  | ||||
| 	/// A completed rule that can be used to test a Garden | ||||
| 	export interface ProducedStatement<T> { | ||||
| 		test(g: Garden): StateTestResult; | ||||
| 		description: string; | ||||
| 		children: T; | ||||
|  | ||||
| 		hasPassedAndFailed(): boolean; | ||||
| 	} | ||||
|  | ||||
| 	function rnd(max: number) { | ||||
| 		return Math.floor(Math.random() * max); | ||||
| 	} | ||||
|  | ||||
| 	function randomColor(): Gardens.RockColor { | ||||
| 		return Math.floor(Math.random() * (Gardens.RockColor.Max - 1)) + 1 | ||||
| 	} | ||||
|  | ||||
| 	function randomShape(): Gardens.RockShape { | ||||
| 		return Math.floor(Math.random() * (Gardens.RockShape.Max - 1)) + 1 | ||||
| 	} | ||||
|  | ||||
| 	/* New Impl Here */ | ||||
| 	interface SelectorSpec<T> { | ||||
| 		childTypes?: PartType[]; | ||||
| 		precedence: number; | ||||
| 		weight: number; | ||||
| 		test(args: T, g: Garden, index: number): string|number|boolean; | ||||
| 		describe(args: T, context: DescribeContext): string; | ||||
| 		isAllValues(values: Array<string>|Array<number>): boolean; | ||||
| 	} | ||||
|  | ||||
| 	interface ProducedSelector { | ||||
| 		test(g: Garden, index: number): string|number|boolean; | ||||
| 		getDescription(plural: DescribeContext): string; | ||||
| 		seenAllValues(): boolean; | ||||
| 	} | ||||
|  | ||||
| 	export function buildSelector<T>(spec: SelectorSpec<T>, args: T): ProducedSelector { | ||||
| 		let seenResults: { [s: string]: boolean;} = {}; | ||||
| 		return { | ||||
| 			test: (g: Garden, index: number) => { | ||||
| 				var result = spec.test(args, g, index); | ||||
| 				seenResults[result + ''] = true; | ||||
| 				return result; | ||||
| 			}, | ||||
| 			getDescription: (context) => { | ||||
| 				return spec.describe(args, context); | ||||
| 			}, | ||||
| 			seenAllValues: () => { | ||||
| 				return spec.isAllValues(Object.keys(seenResults)); | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	export var SelectorTemplates: Array<SelectorSpec<{}>> = []; | ||||
| 	module LetsMakeSomeSelectors { | ||||
| 		// Is rock | ||||
| 		SelectorTemplates.push({ | ||||
| 			test: (args, g, i) => g.colors[i] !== Gardens.RockColor.Empty, | ||||
| 			describe: (args, context) => { | ||||
| 				switch(context) { | ||||
| 					case DescribeContext.Plural: | ||||
| 						return 'Stones'; | ||||
| 					case DescribeContext.Adjectival: | ||||
| 						return 'not empty'; | ||||
| 					case DescribeContext.Singular: | ||||
| 						return 'Stone'; | ||||
| 				} | ||||
| 			}, | ||||
| 			isAllValues: items => items.length === 2, | ||||
| 			precedence: 0, | ||||
| 			weight: 1 | ||||
| 		}); | ||||
|  | ||||
| 		// Is of a certain color and/or shape | ||||
| 		Gardens.RockColorsAndEmpty.forEach(color => { | ||||
| 			let colorName = Gardens.RockColor[color]; | ||||
| 			let colorWeight = color === Gardens.RockColor.Empty ? 1 : 0.33; | ||||
| 			Gardens.RockShapesAndEmpty.forEach(shape => { | ||||
| 				let shapeName = Gardens.RockShape[shape]; | ||||
| 				let shapeWeight = shape === Gardens.RockShape.Empty ? 1 : 0.33; | ||||
| 				SelectorTemplates.push({ | ||||
| 					test: (args, g, i) => { | ||||
| 						if(color === Gardens.RockColor.Empty) { | ||||
| 							if (shape === Gardens.RockShape.Empty) { | ||||
| 								return g.colors[i] === Gardens.RockColor.Empty; | ||||
| 							} else { | ||||
| 								return g.shapes[i] === shape; | ||||
| 							} | ||||
| 						} else { | ||||
| 							if (shape === Gardens.RockShape.Empty) { | ||||
| 								return g.colors[i] === color; | ||||
| 							} else { | ||||
| 								return g.shapes[i] === shape && g.colors[i] === color; | ||||
| 							} | ||||
| 						} | ||||
| 					}, | ||||
| 					describe: (args, context) => { | ||||
| 						if(color === Gardens.RockColor.Empty) { | ||||
| 							if (shape === Gardens.RockShape.Empty) { | ||||
| 								switch(context) { | ||||
| 									case DescribeContext.Plural: | ||||
| 										return 'Empty Cells'; | ||||
| 									case DescribeContext.Adjectival: | ||||
| 										return 'Empty'; | ||||
| 									case DescribeContext.Singular: | ||||
| 										return 'Empty Cell'; | ||||
| 								} | ||||
| 							} else { | ||||
| 								switch(context) { | ||||
| 									case DescribeContext.Plural: | ||||
| 										return shapeName + 's'; | ||||
| 									case DescribeContext.Adjectival: | ||||
| 										return 'a ' + shapeName; | ||||
| 									case DescribeContext.Singular: | ||||
| 										return shapeName; | ||||
| 								} | ||||
| 							} | ||||
| 						} else { | ||||
| 							if (shape === Gardens.RockShape.Empty) { | ||||
| 								switch(context) { | ||||
| 									case DescribeContext.Plural: | ||||
| 										return colorName + ' Stones'; | ||||
| 									case DescribeContext.Adjectival: | ||||
| 										return colorName; | ||||
| 									case DescribeContext.Singular: | ||||
| 										return colorName + ' Stone'; | ||||
| 								} | ||||
| 							} else { | ||||
| 								switch(context) { | ||||
| 									case DescribeContext.Plural: | ||||
| 										return colorName + ' ' + shapeName + 's'; | ||||
| 									case DescribeContext.Adjectival: | ||||
| 										return 'a ' + colorName + ' ' + shapeName; | ||||
| 									case DescribeContext.Singular: | ||||
| 										return colorName + ' ' + shapeName; | ||||
| 								} | ||||
| 							} | ||||
| 						} | ||||
| 					}, | ||||
| 					isAllValues: items => items.length === 2, | ||||
| 					precedence: 3, | ||||
| 					weight: (shapeWeight + colorWeight === 2) ? 0.3 : shapeWeight * colorWeight | ||||
| 				}); | ||||
| 			}); | ||||
| 		}); | ||||
|  | ||||
| 		// [?] in the [top|middle|bottom] [row|column] | ||||
| 		[0, 1, 2].forEach(rowCol => { | ||||
| 			[true, false].forEach(isRow => { | ||||
| 				var name = (isRow ? ['top', 'middle', 'bottom'] : ['left', 'middle', 'right'])[rowCol] + ' ' + (isRow ? 'row' : 'column'); | ||||
| 				var spec: SelectorSpec<[ProducedSelector]> = { | ||||
| 					childTypes: [PartType.Selector], | ||||
| 					test: (args, g, i) => { | ||||
| 						var c = isRow ? Math.floor(i / 3) : i % 3; | ||||
| 						if (c === rowCol) { | ||||
| 							return args[0].test(g, i); | ||||
| 						} else { | ||||
| 							return false; | ||||
| 						} | ||||
| 					}, | ||||
| 					describe: (args, plural) => args[0].getDescription(plural) + ' in the ' + name, | ||||
| 					isAllValues: items => items.length === 2, | ||||
| 					precedence: 4, | ||||
| 					weight: 1 / 6 | ||||
| 				}; | ||||
| 				SelectorTemplates.push(spec); | ||||
| 			}); | ||||
| 		}); | ||||
|  | ||||
| 		// [?] next to a [?] | ||||
| 		SelectorTemplates.push({ | ||||
| 			childTypes: [PartType.Selector, PartType.Selector], | ||||
| 			test: (args, g, i) => { | ||||
| 				if (args[0].test(g, i)) { | ||||
| 					return Gardens.adjacencies[i].some(x => !!args[1].test(g, x)); | ||||
| 				} else { | ||||
| 					return false; | ||||
| 				} | ||||
| 			}, | ||||
| 			describe: (args, plural) => { | ||||
| 				return args[0].getDescription(plural) + ' next to a ' + args[1].getDescription(DescribeContext.Singular); | ||||
| 			}, | ||||
| 			isAllValues: items => items.length === 2, | ||||
| 			precedence: 4, | ||||
| 			weight: 1 | ||||
| 		} as SelectorSpec<[ProducedSelector, ProducedSelector]>); | ||||
| 	} | ||||
|  | ||||
| 	export function buildStatement<T>(s: StatementTemplate<T>, args: T): ProducedStatement<T> { | ||||
| 		let hasPassed = false; | ||||
| 		let hasFailed = false; | ||||
|  | ||||
| 		let result: ProducedStatement<T> = { | ||||
| 			children: args, | ||||
| 			description: s.describe(args), | ||||
| 			test: (g) => { | ||||
| 				let r = s.test(g, args); | ||||
| 				if (r === StateTestResult.Pass) { | ||||
| 					hasPassed = true; | ||||
| 				} else if(r === StateTestResult.Fail) { | ||||
| 					hasFailed = true; | ||||
| 				} | ||||
| 				return r; | ||||
| 			}, | ||||
| 			hasPassedAndFailed: () => { | ||||
| 				return hasPassed && hasFailed && (args as any as ProducedSelector[]).every(c => c.seenAllValues()); | ||||
| 			} | ||||
| 		}; | ||||
| 		return result; | ||||
| 	} | ||||
|  | ||||
| 	export let StatementList: StatementTemplate<any>[] = []; | ||||
| 	module LetsMakeSomeStatements { | ||||
| 		// Every [?] is a [?] | ||||
| 		StatementList.push({ | ||||
| 			holes: [PartType.Selector, PartType.Selector], | ||||
| 			test: (g: Garden, args: [ProducedSelector, ProducedSelector]) => { | ||||
| 				let didAnyTests = false; | ||||
| 				for (var i = 0; i < Gardens.Size; i++) { | ||||
| 					if (args[0].test(g, i)) { | ||||
| 						if(!args[1].test(g, i)) return StateTestResult.Fail; | ||||
| 						didAnyTests = true; | ||||
| 					} | ||||
| 				} | ||||
| 				return didAnyTests ? StateTestResult.Pass : StateTestResult.WeakPass; | ||||
| 			}, | ||||
| 			describe: args => { | ||||
| 				return 'Every ' + args[0].getDescription(DescribeContext.Singular) + ' is ' + args[1].getDescription(DescribeContext.Adjectival); | ||||
| 			} | ||||
| 		}); | ||||
|  | ||||
| 		// There is exactly 1 [?] | ||||
| 		StatementList.push({ | ||||
| 			holes: [PartType.Selector], | ||||
| 			test: (g: Garden, args: [ProducedSelector, ProducedSelector]) => { | ||||
| 				var count = 0; | ||||
| 				for (var i = 0; i < Gardens.Size; i++) { | ||||
| 					if (args[0].test(g, i)) count++; | ||||
| 				} | ||||
|  | ||||
| 				return count === 1 ? StateTestResult.Pass : StateTestResult.Fail; | ||||
| 			}, | ||||
| 			describe: args => { | ||||
| 				return 'There is exactly one ' + args[0].description; | ||||
| 			} | ||||
| 		}); | ||||
|  | ||||
| 		// There are more [?] than [?] | ||||
| 		StatementList.push({ | ||||
| 			holes: [PartType.Selector, PartType.Selector], | ||||
| 			test: (g: Garden, args: [ProducedSelector, ProducedSelector]) => { | ||||
| 				var p1c = 0, p2c = 0; | ||||
| 				for (var i = 0; i < Gardens.Size; i++) { | ||||
| 					if (args[0].test(g, i)) p1c++; | ||||
| 					if (args[1].test(g, i)) p2c++; | ||||
| 				} | ||||
| 				if(p1c > p2c && p2c > 0) { | ||||
| 					return StateTestResult.Pass; | ||||
| 				} else if(p1c > p2c) { | ||||
| 					return StateTestResult.WeakPass; | ||||
| 				} else { | ||||
| 					return StateTestResult.Fail; | ||||
| 				} | ||||
| 			}, | ||||
| 			describe: args => { | ||||
| 				return 'There are more ' + args[0].descriptionPlural + ' than ' + args[1].descriptionPlural; | ||||
| 			} | ||||
| 		}); | ||||
| 	} | ||||
|  | ||||
| 	function randomElementOf<T>(arr: T[]): T { | ||||
| 		if (arr.length === 0) { | ||||
| 			return undefined; | ||||
| 		} else { | ||||
| 			return arr[Math.floor(Math.random() * arr.length)]; | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	function randomWeightedElementOf<T extends { weight: number }>(arr: T[]): T { | ||||
| 		var totalWeight = arr.reduce((acc, v) => acc + v.weight, 0); | ||||
| 		var rnd = Math.random() * totalWeight; | ||||
| 		for (var i = 0; i < arr.length; i++) { | ||||
| 			rnd -= arr[i].weight; | ||||
| 			if (rnd <= 0) return arr[i]; | ||||
| 		} | ||||
| 		// Got destroyed by floating error, just try again | ||||
| 		return randomWeightedElementOf(arr); | ||||
| 	} | ||||
|  | ||||
| 	export function buildRandomNewSelector(maxPrecedence = 1000000): ProducedSelector { | ||||
| 		var choices = SelectorTemplates; | ||||
|  | ||||
| 		let initial = randomWeightedElementOf(choices.filter(p => p.precedence <= maxPrecedence)); | ||||
| 		// Fill in the holes | ||||
| 		if (initial.childTypes) { | ||||
| 			var fills = initial.childTypes.map(h => { | ||||
| 				if (h === PartType.Selector) { | ||||
| 					return buildRandomNewSelector(initial.precedence - 1); | ||||
| 				} else { | ||||
| 					throw new Error('Only know how to fill Selector holes') | ||||
| 				} | ||||
| 			}); | ||||
| 			return buildSelector(initial, fills); | ||||
| 		} else { | ||||
| 			return buildSelector(initial, []); | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	export function makeEmptyGarden(): Garden { | ||||
| 		var g = {} as Garden; | ||||
| 		g.colors = []; | ||||
| 		g.shapes = []; | ||||
| 		for (var i = 0; i < Gardens.Size; i++) { | ||||
| 			g.colors.push(Gardens.RockColor.Empty); | ||||
| 			g.shapes.push(Gardens.RockShape.Empty); | ||||
| 		} | ||||
|  | ||||
| 		return g; | ||||
| 	} | ||||
|  | ||||
| 	export function gardenToString(g: Garden): string { | ||||
| 		return g.colors.join('') + g.shapes.join(''); | ||||
| 	} | ||||
|  | ||||
| 	export function makeRandomGarden(): Garden { | ||||
| 		var g = makeEmptyGarden(); | ||||
| 		blitRandomGardenPair(g, g); | ||||
| 		return g; | ||||
| 	} | ||||
|  | ||||
| 	export function cloneGarden(g: Garden): Garden { | ||||
| 		var result: Garden = { | ||||
| 			colors: g.colors.slice(0), | ||||
| 			shapes: g.shapes.slice(0) | ||||
| 		}; | ||||
| 		return result; | ||||
| 	} | ||||
|  | ||||
| 	export function clearGarden(g: Garden) { | ||||
| 		for (var i = 0; i < Gardens.Size; i++) { | ||||
| 			g.colors[i] = Gardens.RockColor.Empty; | ||||
| 			g.shapes[i] = Gardens.RockShape.Empty; | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	export function blitRandomGardenPair(g1: Garden, g2: Garden): void { | ||||
| 		let placeCount = 0; | ||||
| 		for (var i = 0; i < Gardens.Size; i++) { | ||||
| 			if (rnd(7) === 0) { | ||||
| 				g1.colors[i] = g2.colors[i] = randomColor(); | ||||
| 				g1.shapes[i] = g2.shapes[i] = randomShape(); | ||||
| 			} else { | ||||
| 				placeCount++; | ||||
| 				g1.colors[i] = g2.colors[i] = Gardens.RockColor.Empty; | ||||
| 				g1.shapes[i] = g2.shapes[i] = Gardens.RockShape.Empty; | ||||
| 			} | ||||
| 		} | ||||
| 		if (placeCount === 0) blitRandomGardenPair(g1, g2); | ||||
| 	} | ||||
|  | ||||
| 	export function blitNumberedGarden(g: Garden, stoneCount: number, n: number): void { | ||||
| 		clearGarden(g); | ||||
|  | ||||
| 		let cellNumbers = [0, 1, 2, 3, 4, 5, 6, 7, 8]; | ||||
| 		for (let i = 0; i < stoneCount; i++) { | ||||
| 			let cellNum = getValue(cellNumbers.length); | ||||
| 			let cell = cellNumbers.splice(cellNum, 1)[0]; | ||||
| 			g.colors[cell] = getValue(3) + 1; | ||||
| 			g.shapes[cell] = getValue(3) + 1; | ||||
| 		} | ||||
|  | ||||
| 		function getValue(max: number) { | ||||
| 			let result = n % max; | ||||
| 			n = (n - result) / max; | ||||
| 			return result; | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	export function mutateGarden(g: Garden): void { | ||||
| 		while (true) { | ||||
| 			var op = rnd(5); | ||||
| 			let x = rnd(Gardens.Size); | ||||
| 			let y = rnd(Gardens.Size); | ||||
| 			switch (op) { | ||||
| 				case 0: // Swap two non-identical cells | ||||
| 					if (g.colors[x] !== g.colors[y] || g.shapes[x] !== g.shapes[y]) { | ||||
| 						var tmp: any = g.colors[x]; | ||||
| 						g.colors[x] = g.colors[y]; | ||||
| 						g.colors[y] = tmp; | ||||
| 						tmp = g.shapes[x]; | ||||
| 						g.shapes[x] = g.shapes[y]; | ||||
| 						g.shapes[y] = tmp; | ||||
| 						return; | ||||
| 					} | ||||
| 					break; | ||||
| 				case 1: // Add a stone | ||||
| 					if (g.colors[x] === Gardens.RockColor.Empty) { | ||||
| 						g.colors[x] = randomColor(); | ||||
| 						g.shapes[x] = randomShape(); | ||||
| 						return; | ||||
| 					} | ||||
| 					break; | ||||
| 				case 2: // Remove a stone | ||||
| 					if (g.colors.filter(x => x !== Gardens.RockColor.Empty).length === 1) continue; | ||||
|  | ||||
| 					if (g.colors[x] !== Gardens.RockColor.Empty) { | ||||
| 						g.colors[x] = Gardens.RockColor.Empty; | ||||
| 						g.shapes[x] = Gardens.RockShape.Empty; | ||||
| 						return; | ||||
| 					} | ||||
| 					break; | ||||
| 				case 3: // Change a color | ||||
| 					let c = randomColor(); | ||||
| 					if (g.colors[x] !== Gardens.RockColor.Empty && g.colors[x] !== c) { | ||||
| 						g.colors[x] = c; | ||||
| 						return; | ||||
| 					} | ||||
| 					break; | ||||
| 				case 4: // Change a shape | ||||
| 					let s = randomShape(); | ||||
| 					if (g.shapes[x] !== Gardens.RockShape.Empty && g.shapes[x] !== s) { | ||||
| 						g.shapes[x] = s; | ||||
| 						return; | ||||
| 					} | ||||
| 					break; | ||||
| 			} | ||||
| 		} | ||||
| 	} | ||||
| } | ||||
|  | ||||
| class Indexion { | ||||
| 	sizes: number[]; | ||||
| 	constructor(...sizes: number[]) { | ||||
| 		this.sizes = sizes; | ||||
| 	} | ||||
|  | ||||
| 	public getValues(index: number): number[] { | ||||
| 		let result = new Array<number>(this.sizes.length); | ||||
| 		this.fillValues(index, result); | ||||
| 		return result; | ||||
| 	} | ||||
|  | ||||
| 	public fillValues(index: number, result: number[]): void { | ||||
| 		for (var i = 0; i < this.sizes.length; i++) { | ||||
| 			result[i] = index % this.sizes[i]; | ||||
| 			index -= result[i]; | ||||
| 			index /= this.sizes[i]; | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	public valuesToIndex(values: number[]): number { | ||||
| 		var result = 0; | ||||
| 		var factor = 1; | ||||
| 		for (var i = 0; i < this.sizes.length; i++) { | ||||
| 			result += values[i] * this.sizes[i] * factor; | ||||
| 			factor *= this.sizes[i]; | ||||
| 		} | ||||
| 		return result; | ||||
| 	} | ||||
|  | ||||
| 	public getAdjacentIndices(index: number): number[][] { | ||||
| 		var baseline = this.getValues(index); | ||||
| 		var results: number[][] = []; | ||||
| 		for (var i = 0; i < this.sizes.length; i++) { | ||||
| 			if(baseline[i] > 0) { | ||||
| 				baseline[i]--; | ||||
| 				results.push(baseline.slice()); | ||||
| 				baseline[i]++; | ||||
| 			} | ||||
| 			if(baseline[i] < this.sizes[i] - 1) { | ||||
| 				baseline[i]++; | ||||
| 				results.push(baseline.slice()); | ||||
| 				baseline[i]--; | ||||
| 			} | ||||
| 		} | ||||
| 		return results; | ||||
| 	} | ||||
|  | ||||
| 	public distance(index1: number, index2: number): number { | ||||
| 		let delta = 0; | ||||
| 		for (var i = 0; i < this.sizes.length; i++) { | ||||
| 			var a = index1 % this.sizes[i]; | ||||
| 			var b = index2 % this.sizes[i]; | ||||
| 			delta += Math.abs(b - a); | ||||
| 			index1 -= a; | ||||
| 			index2 -= b; | ||||
| 			index1 /= this.sizes[i]; | ||||
| 			index2 /= this.sizes[i]; | ||||
| 		} | ||||
| 		return delta; | ||||
| 	} | ||||
| } | ||||
|  | ||||
|  | ||||
| function makeNewExample() { | ||||
| 	while (true) { | ||||
| 		var p1 = Koan.buildSelector(Koan.SelectorTemplates[12], []); | ||||
| 		var p2 = Koan.buildSelector(Koan.SelectorTemplates[14], []); | ||||
| 		var test = Koan.buildStatement(Koan.StatementList[0], [p1, p2]); | ||||
|  | ||||
| 		var examples: Garden[] = []; | ||||
|  | ||||
| 		console.log('Attempt to generate examples for "' + test.description + '"'); | ||||
|  | ||||
| 		var maxGarden = /*(9 * 9) + (9 * 9 * 9 * 8) + */(9 * 9 * 9 * 8 * 9 * 7); | ||||
| 		let g = Koan.makeEmptyGarden(); | ||||
| 		let passCount = 0, failCount = 0; | ||||
| 		let resultLookup: boolean[] = []; | ||||
| 		let lastResult: boolean = undefined; | ||||
| 		for (var i = 0; i < maxGarden; i++) { | ||||
| 			Koan.blitNumberedGarden(g, 3, i); | ||||
| 			let result = test.test(g); | ||||
| 			if(result === Koan.StateTestResult.Pass) { | ||||
| 				resultLookup[i] = true; | ||||
| 				passCount++; | ||||
|  | ||||
| 				if (lastResult !== true && examples.length < 10) examples.push(Koan.cloneGarden(g)); | ||||
| 				lastResult = true; | ||||
| 			} else if (result === Koan.StateTestResult.Fail) { | ||||
| 				resultLookup[i] = false; | ||||
| 				failCount++; | ||||
|  | ||||
| 				if (lastResult !== false && examples.length < 10) examples.push(Koan.cloneGarden(g)); | ||||
| 				lastResult = false; | ||||
| 			} | ||||
|  | ||||
| 			if (examples.length === 10) break; | ||||
| 		} | ||||
|  | ||||
| 		console.log('Rule passes ' + passCount + ' and fails ' + failCount); | ||||
|  | ||||
| 		/* | ||||
| 		if (!test.hasPassedAndFailed()) { | ||||
| 			console.log('Rule has unreachable, contradictory, or tautological clauses'); | ||||
| 			continue; | ||||
| 		} | ||||
|  | ||||
| 		if (passCount === 0 || failCount === 0) { | ||||
| 			console.log('Rule is always true or always false'); | ||||
| 			continue; | ||||
| 		} | ||||
| 		*/ | ||||
|  | ||||
| 		var h = document.createElement('h2'); | ||||
| 		h.innerText = test.description; | ||||
| 		document.body.appendChild(h); | ||||
|  | ||||
| 		return { test: test, examples: examples }; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| let list: Garden[] = []; | ||||
| let test: Koan.ProducedStatement<any>; | ||||
| window.onload = function() { | ||||
| 	let rule = makeNewExample(); | ||||
| 	let garden = Koan.makeRandomGarden(); | ||||
| 	list = rule.examples; | ||||
| 	test = rule.test; | ||||
|  | ||||
| 	function renderList() { | ||||
| 		function makeGarden(g: Garden, i: number) { | ||||
| 			return <GardenDisplay | ||||
| 				garden={g} | ||||
| 				key={i + Koan.gardenToString(g)} | ||||
| 				test={test} | ||||
| 				leftButton='✗' | ||||
| 				rightButton='✎' | ||||
| 				onLeftButtonClicked={() => { | ||||
| 					console.log(list.indexOf(g)); | ||||
| 					list.splice(list.indexOf(g), 1); | ||||
| 					renderList(); | ||||
| 				}} | ||||
| 				onRightButtonClicked={() => { | ||||
| 					garden = g; | ||||
| 					renderEditor(); | ||||
| 				}} | ||||
| 			/>; | ||||
| 		} | ||||
| 		let gardenList = <div>{list.map(makeGarden)}</div>; | ||||
| 		React.render(gardenList, document.getElementById('results')); | ||||
| 	} | ||||
|  | ||||
| 	let i = 0; | ||||
| 	function renderEditor() { | ||||
| 		i++; | ||||
| 		let editor = <GardenEditor key={i} test={rule.test} garden={garden} onSaveClicked={(garden) => { | ||||
| 			list.push(garden); | ||||
| 			renderList(); | ||||
| 		}} />; | ||||
| 		React.render(editor, document.getElementById('editor')); | ||||
| 	} | ||||
|  | ||||
| 	renderList(); | ||||
| 	renderEditor(); | ||||
| } | ||||
|  | ||||
| function classNames(nameMap: any): string { | ||||
| 	return Object.keys(nameMap).filter(k => nameMap[k]).join(' '); | ||||
| } | ||||
|  | ||||
| interface GardenCellProps extends React.Props<{}> { | ||||
| 	color: Gardens.RockColor; | ||||
| 	shape: Gardens.RockShape; | ||||
| 	index: number; | ||||
|  | ||||
| 	movable?: boolean; | ||||
| 	onEdit?(newColor: Gardens.RockColor, newShape: Gardens.RockShape): void; | ||||
| } | ||||
| interface GardenCellState { | ||||
| 	isDragging?: boolean; | ||||
| } | ||||
| class GardenCell extends React.Component<GardenCellProps, GardenCellState> { | ||||
| 	state: GardenCellState = {}; | ||||
| 	ignoreNextEdit = false; | ||||
|  | ||||
| 	render() { | ||||
| 		var classes = ['cell', 'index_' + this.props.index]; | ||||
|  | ||||
| 		if (this.state.isDragging) { | ||||
| 			// Render as blank | ||||
| 		} else { | ||||
| 			classes.push(Gardens.RockColor[this.props.color], Gardens.RockShape[this.props.shape]); | ||||
| 		} | ||||
|  | ||||
| 		if (this.props.movable) classes.push('movable'); | ||||
| 		let events: React.HTMLAttributes = { | ||||
| 			onDragStart: (e) => { | ||||
| 				this.ignoreNextEdit = false; | ||||
| 				e.dataTransfer.dropEffect = 'copyMove'; | ||||
| 				e.dataTransfer.effectAllowed = 'move'; | ||||
| 				e.dataTransfer.setData('shape', this.props.shape.toString()); | ||||
| 				e.dataTransfer.setData('color', this.props.color.toString()); | ||||
|  | ||||
| 				let drag = document.getElementById(getGardenName(this.props.color, this.props.shape)); | ||||
| 				let xfer: any = (e.nativeEvent as DragEvent).dataTransfer; | ||||
| 				xfer.setDragImage(drag, drag.clientWidth * 0.5, drag.clientHeight * 0.5); | ||||
|  | ||||
| 				this.setState({ isDragging: true }); | ||||
| 			}, | ||||
| 			onDragEnter: (e) => { | ||||
| 				e.dataTransfer.dropEffect = 'move'; | ||||
| 				e.preventDefault(); | ||||
| 			}, | ||||
| 			onDragOver: (e) => { | ||||
| 				e.dataTransfer.dropEffect = 'move'; | ||||
| 				e.preventDefault(); | ||||
| 			}, | ||||
| 			onDragEnd: (e) => { | ||||
| 				this.setState({ isDragging: false }); | ||||
| 				if (!this.ignoreNextEdit) { | ||||
| 					this.props.onEdit && this.props.onEdit(undefined, undefined); | ||||
| 				} | ||||
| 			}, | ||||
| 			draggable: true | ||||
| 		} | ||||
|  | ||||
| 		let handleDrop = (event: React.DragEvent) => { | ||||
| 			if(this.props.onEdit) { | ||||
| 				if (this.state.isDragging) { | ||||
| 					// Dragged to self, don't do anything | ||||
| 					this.ignoreNextEdit = true; | ||||
| 				} else { | ||||
| 					let shape: Gardens.RockShape = +event.dataTransfer.getData('shape'); | ||||
| 					let color: Gardens.RockColor = +event.dataTransfer.getData('color'); | ||||
| 					this.props.onEdit(color, shape); | ||||
| 				} | ||||
| 			} | ||||
| 		} | ||||
|  | ||||
| 		return <span className={classes.join(' ')} onDrop={handleDrop} {...this.props.movable ? events : {}} />; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| interface GardenDisplayProps extends React.Props<GardenDisplay> { | ||||
| 	garden?: Garden; | ||||
| 	test?: Koan.ProducedStatement<any>; | ||||
|  | ||||
| 	leftButton?: string; | ||||
| 	rightButton?: string; | ||||
| 	onLeftButtonClicked?(): void; | ||||
| 	onRightButtonClicked?(): void; | ||||
|  | ||||
| 	editable?: boolean; | ||||
| 	onChanged?(newGarden: Garden): void; | ||||
| } | ||||
| interface GardenDisplayState { | ||||
| 	garden?: Garden; | ||||
| } | ||||
| class GardenDisplay extends React.Component<GardenDisplayProps, GardenDisplayState> { | ||||
| 	state = { | ||||
| 		garden: Koan.cloneGarden(this.props.garden) | ||||
| 	}; | ||||
|  | ||||
| 	leftClicked = () => { | ||||
| 		this.props.onLeftButtonClicked && this.props.onLeftButtonClicked(); | ||||
| 	}; | ||||
|  | ||||
| 	rightClicked = () => { | ||||
| 		this.props.onRightButtonClicked && this.props.onRightButtonClicked(); | ||||
| 	}; | ||||
|  | ||||
| 	render() { | ||||
| 		let g = this.state.garden; | ||||
| 		let pass = (this.props.test && this.props.test.test(this.state.garden)); | ||||
|  | ||||
| 		let classes = { | ||||
| 			garden: true, | ||||
| 			unknown: pass === undefined, | ||||
| 			pass: pass === Koan.StateTestResult.Pass || pass === Koan.StateTestResult.WeakPass, | ||||
| 			fail: pass === Koan.StateTestResult.Fail, | ||||
| 			editable: this.props.editable | ||||
| 		}; | ||||
|  | ||||
| 		var children = g.colors.map((_, i) => ( | ||||
| 			<GardenCell | ||||
| 				key={i} | ||||
| 				color={g.colors[i]} | ||||
| 				shape={g.shapes[i]} | ||||
| 				index={i} | ||||
| 				movable={this.props.editable} | ||||
| 				onEdit={(newColor, newShape) => { | ||||
| 					if(this.props.editable) { | ||||
| 						let newGarden = Koan.cloneGarden(this.state.garden); | ||||
| 						newGarden.colors[i] = newColor; | ||||
| 						newGarden.shapes[i] = newShape; | ||||
| 						this.setState({ garden: newGarden }); | ||||
| 						this.props.onChanged && this.props.onChanged(newGarden); | ||||
| 					} | ||||
| 				}} | ||||
| 			/>)); | ||||
|  | ||||
| 		return <div className="gardenDisplay"> | ||||
| 			<div className={classNames(classes)}>{children}</div> | ||||
| 			<span className="infoRow"> | ||||
| 				{this.props.leftButton && <div className="button left" onClick={this.leftClicked}>{this.props.leftButton}</div>} | ||||
| 				<div className={"passfail " + (pass ? 'pass' : 'fail')}>{pass ? '✓' : '🚫'}</div> | ||||
| 				{this.props.rightButton && <div className="button right" onClick={this.rightClicked}>{this.props.rightButton}</div>} | ||||
| 			</span> | ||||
| 		</div>; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| interface GardenEditorProps extends React.Props<GardenEditor> { | ||||
| 	onSaveClicked?(garden: Garden): void; | ||||
| 	test?: Koan.ProducedStatement<any>; | ||||
| 	garden?: Garden; | ||||
| } | ||||
| interface GardenEditorState { | ||||
| 	garden?: Garden; | ||||
| 	pass?: boolean; | ||||
| } | ||||
| class GardenEditor extends React.Component<GardenEditorProps, {}> { | ||||
| 	state = { garden: this.props.garden }; | ||||
|  | ||||
| 	save = () => { | ||||
| 		this.props.onSaveClicked && this.props.onSaveClicked(this.state.garden); | ||||
| 	}; | ||||
|  | ||||
| 	render() { | ||||
| 		return <div className="editor"> | ||||
| 			<GardenDisplay garden={this.state.garden} test={this.props.test} editable onChanged={g => this.setState({ garden: g }) } /> | ||||
| 			<StonePalette /> | ||||
| 			<div className="button save" onClick={this.save}>{'💾'}</div> | ||||
| 		</div>; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| class StonePalette extends React.Component<{}, {}> { | ||||
| 	render() { | ||||
| 		let items: JSX.Element[] = []; | ||||
| 		Gardens.RockColors.forEach(color => { | ||||
| 			Gardens.RockShapes.forEach(shape => { | ||||
| 				let name = getGardenName(color, shape); | ||||
| 				let extraProps = { id: name, key: name }; | ||||
| 				let index = items.length; | ||||
| 				items.push(<GardenCell | ||||
| 					color={color} | ||||
| 					shape={shape} | ||||
| 					index={index} | ||||
| 					movable | ||||
| 					{...extraProps} />) | ||||
| 			}); | ||||
| 		}); | ||||
| 		return <div className="palette">{items}</div>; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| function getGardenName(color: Gardens.RockColor, shape: Gardens.RockShape) { | ||||
| 	return 'draggable.' + Gardens.RockShape[shape] + '.' + Gardens.RockColor[color]; | ||||
| } | ||||
|  | ||||
|  | ||||
| @@ -1,27 +0,0 @@ | ||||
| //@jsx: preserve | ||||
| //@module: amd | ||||
|  | ||||
| //@filename: react.d.ts | ||||
| declare module JSX { | ||||
| 	interface Element { } | ||||
| 	interface IntrinsicElements { | ||||
| 	} | ||||
| 	interface ElementAttributesProperty { | ||||
| 		props; | ||||
| 	} | ||||
| } | ||||
|  | ||||
| interface Props {   | ||||
|   foo: string; | ||||
| } | ||||
|  | ||||
| //@filename: file.tsx | ||||
| export class MyComponent {   | ||||
|   render() { | ||||
|   } | ||||
|  | ||||
|   props: { foo: string; } | ||||
| } | ||||
|  | ||||
| <MyComponent foo="bar" />; // ok   | ||||
| <MyComponent foo={0} />; // should be an error | ||||
| @@ -53,4 +53,8 @@ class TestClassifier < Minitest::Test | ||||
|       assert_equal language.name, results.first[0], "#{sample[:path]}\n#{results.inspect}" | ||||
|     end | ||||
|   end | ||||
|  | ||||
|   def test_classify_empty_languages | ||||
|     assert_equal [], Classifier.classify(Samples.cache, fixture("Ruby/foo.rb"), []) | ||||
|   end | ||||
| end | ||||
|   | ||||
| @@ -264,4 +264,11 @@ class TestHeuristcs < Minitest::Test | ||||
|       "XML" => all_fixtures("XML", "*.ts") | ||||
|     }) | ||||
|   end | ||||
|  | ||||
|   def test_tsx_by_heuristics | ||||
|     assert_heuristics({ | ||||
|       "TypeScript" => all_fixtures("TypeScript", "*.tsx"), | ||||
|       "XML" => all_fixtures("XML", "*.tsx") | ||||
|     }) | ||||
|   end | ||||
| end | ||||
|   | ||||
							
								
								
									
										2
									
								
								vendor/README.md
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										2
									
								
								vendor/README.md
									
									
									
									
										vendored
									
									
								
							| @@ -142,7 +142,7 @@ This is a list of grammars that Linguist selects to provide syntax highlighting | ||||
| - **Harbour:** [hernad/atom-language-harbour](https://github.com/hernad/atom-language-harbour) | ||||
| - **Haskell:** [atom-haskell/language-haskell](https://github.com/atom-haskell/language-haskell) | ||||
| - **Haxe:** [clemos/haxe-sublime-bundle](https://github.com/clemos/haxe-sublime-bundle) | ||||
| - **HCL:** [aroben/ruby.tmbundle](https://github.com/aroben/ruby.tmbundle) | ||||
| - **HCL:** [alexlouden/Terraform.tmLanguage](https://github.com/alexlouden/Terraform.tmLanguage) | ||||
| - **HTML:** [textmate/html.tmbundle](https://github.com/textmate/html.tmbundle) | ||||
| - **HTML+Django:** [textmate/python-django.tmbundle](https://github.com/textmate/python-django.tmbundle) | ||||
| - **HTML+ECR:** [atom-crystal/language-crystal](https://github.com/atom-crystal/language-crystal) | ||||
|   | ||||
							
								
								
									
										2
									
								
								vendor/grammars/TXL
									
									
									
									
										vendored
									
									
								
							
							
								
								
								
								
								
							
						
						
									
										2
									
								
								vendor/grammars/TXL
									
									
									
									
										vendored
									
									
								
							 Submodule vendor/grammars/TXL updated: c1c98dfa86...614cf83649
									
								
							
							
								
								
									
										1
									
								
								vendor/grammars/Terraform.tmLanguage
									
									
									
									
										vendored
									
									
										Submodule
									
								
							
							
								
								
								
								
								
							
						
						
									
										1
									
								
								vendor/grammars/Terraform.tmLanguage
									
									
									
									
										vendored
									
									
										Submodule
									
								
							 Submodule vendor/grammars/Terraform.tmLanguage added at 93b11ff8ab
									
								
							
							
								
								
									
										1
									
								
								vendor/grammars/language-meson
									
									
									
									
										vendored
									
									
										Submodule
									
								
							
							
								
								
								
								
								
							
						
						
									
										1
									
								
								vendor/grammars/language-meson
									
									
									
									
										vendored
									
									
										Submodule
									
								
							 Submodule vendor/grammars/language-meson added at 017bf353f2
									
								
							
							
								
								
									
										1
									
								
								vendor/grammars/shaders-tmLanguage
									
									
									
									
										vendored
									
									
										Submodule
									
								
							
							
								
								
								
								
								
							
						
						
									
										1
									
								
								vendor/grammars/shaders-tmLanguage
									
									
									
									
										vendored
									
									
										Submodule
									
								
							 Submodule vendor/grammars/shaders-tmLanguage added at cd1ef40f54
									
								
							
							
								
								
									
										26
									
								
								vendor/licenses/grammar/Terraform.tmLanguage.txt
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										26
									
								
								vendor/licenses/grammar/Terraform.tmLanguage.txt
									
									
									
									
										vendored
									
									
										Normal file
									
								
							| @@ -0,0 +1,26 @@ | ||||
| --- | ||||
| type: grammar | ||||
| name: Terraform.tmLanguage | ||||
| license: mit | ||||
| --- | ||||
| MIT License | ||||
|  | ||||
| Copyright (c) 2016 Alex Louden | ||||
|  | ||||
| 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. | ||||
							
								
								
									
										206
									
								
								vendor/licenses/grammar/language-meson.txt
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										206
									
								
								vendor/licenses/grammar/language-meson.txt
									
									
									
									
										vendored
									
									
										Normal file
									
								
							| @@ -0,0 +1,206 @@ | ||||
| --- | ||||
| type: grammar | ||||
| name: language-meson | ||||
| license: apache-2.0 | ||||
| --- | ||||
| Apache License | ||||
|                            Version 2.0, January 2004 | ||||
|                         http://www.apache.org/licenses/ | ||||
|  | ||||
|    TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION | ||||
|  | ||||
|    1. Definitions. | ||||
|  | ||||
|       "License" shall mean the terms and conditions for use, reproduction, | ||||
|       and distribution as defined by Sections 1 through 9 of this document. | ||||
|  | ||||
|       "Licensor" shall mean the copyright owner or entity authorized by | ||||
|       the copyright owner that is granting the License. | ||||
|  | ||||
|       "Legal Entity" shall mean the union of the acting entity and all | ||||
|       other entities that control, are controlled by, or are under common | ||||
|       control with that entity. For the purposes of this definition, | ||||
|       "control" means (i) the power, direct or indirect, to cause the | ||||
|       direction or management of such entity, whether by contract or | ||||
|       otherwise, or (ii) ownership of fifty percent (50%) or more of the | ||||
|       outstanding shares, or (iii) beneficial ownership of such entity. | ||||
|  | ||||
|       "You" (or "Your") shall mean an individual or Legal Entity | ||||
|       exercising permissions granted by this License. | ||||
|  | ||||
|       "Source" form shall mean the preferred form for making modifications, | ||||
|       including but not limited to software source code, documentation | ||||
|       source, and configuration files. | ||||
|  | ||||
|       "Object" form shall mean any form resulting from mechanical | ||||
|       transformation or translation of a Source form, including but | ||||
|       not limited to compiled object code, generated documentation, | ||||
|       and conversions to other media types. | ||||
|  | ||||
|       "Work" shall mean the work of authorship, whether in Source or | ||||
|       Object form, made available under the License, as indicated by a | ||||
|       copyright notice that is included in or attached to the work | ||||
|       (an example is provided in the Appendix below). | ||||
|  | ||||
|       "Derivative Works" shall mean any work, whether in Source or Object | ||||
|       form, that is based on (or derived from) the Work and for which the | ||||
|       editorial revisions, annotations, elaborations, or other modifications | ||||
|       represent, as a whole, an original work of authorship. For the purposes | ||||
|       of this License, Derivative Works shall not include works that remain | ||||
|       separable from, or merely link (or bind by name) to the interfaces of, | ||||
|       the Work and Derivative Works thereof. | ||||
|  | ||||
|       "Contribution" shall mean any work of authorship, including | ||||
|       the original version of the Work and any modifications or additions | ||||
|       to that Work or Derivative Works thereof, that is intentionally | ||||
|       submitted to Licensor for inclusion in the Work by the copyright owner | ||||
|       or by an individual or Legal Entity authorized to submit on behalf of | ||||
|       the copyright owner. For the purposes of this definition, "submitted" | ||||
|       means any form of electronic, verbal, or written communication sent | ||||
|       to the Licensor or its representatives, including but not limited to | ||||
|       communication on electronic mailing lists, source code control systems, | ||||
|       and issue tracking systems that are managed by, or on behalf of, the | ||||
|       Licensor for the purpose of discussing and improving the Work, but | ||||
|       excluding communication that is conspicuously marked or otherwise | ||||
|       designated in writing by the copyright owner as "Not a Contribution." | ||||
|  | ||||
|       "Contributor" shall mean Licensor and any individual or Legal Entity | ||||
|       on behalf of whom a Contribution has been received by Licensor and | ||||
|       subsequently incorporated within the Work. | ||||
|  | ||||
|    2. Grant of Copyright License. Subject to the terms and conditions of | ||||
|       this License, each Contributor hereby grants to You a perpetual, | ||||
|       worldwide, non-exclusive, no-charge, royalty-free, irrevocable | ||||
|       copyright license to reproduce, prepare Derivative Works of, | ||||
|       publicly display, publicly perform, sublicense, and distribute the | ||||
|       Work and such Derivative Works in Source or Object form. | ||||
|  | ||||
|    3. Grant of Patent License. Subject to the terms and conditions of | ||||
|       this License, each Contributor hereby grants to You a perpetual, | ||||
|       worldwide, non-exclusive, no-charge, royalty-free, irrevocable | ||||
|       (except as stated in this section) patent license to make, have made, | ||||
|       use, offer to sell, sell, import, and otherwise transfer the Work, | ||||
|       where such license applies only to those patent claims licensable | ||||
|       by such Contributor that are necessarily infringed by their | ||||
|       Contribution(s) alone or by combination of their Contribution(s) | ||||
|       with the Work to which such Contribution(s) was submitted. If You | ||||
|       institute patent litigation against any entity (including a | ||||
|       cross-claim or counterclaim in a lawsuit) alleging that the Work | ||||
|       or a Contribution incorporated within the Work constitutes direct | ||||
|       or contributory patent infringement, then any patent licenses | ||||
|       granted to You under this License for that Work shall terminate | ||||
|       as of the date such litigation is filed. | ||||
|  | ||||
|    4. Redistribution. You may reproduce and distribute copies of the | ||||
|       Work or Derivative Works thereof in any medium, with or without | ||||
|       modifications, and in Source or Object form, provided that You | ||||
|       meet the following conditions: | ||||
|  | ||||
|       (a) You must give any other recipients of the Work or | ||||
|           Derivative Works a copy of this License; and | ||||
|  | ||||
|       (b) You must cause any modified files to carry prominent notices | ||||
|           stating that You changed the files; and | ||||
|  | ||||
|       (c) You must retain, in the Source form of any Derivative Works | ||||
|           that You distribute, all copyright, patent, trademark, and | ||||
|           attribution notices from the Source form of the Work, | ||||
|           excluding those notices that do not pertain to any part of | ||||
|           the Derivative Works; and | ||||
|  | ||||
|       (d) If the Work includes a "NOTICE" text file as part of its | ||||
|           distribution, then any Derivative Works that You distribute must | ||||
|           include a readable copy of the attribution notices contained | ||||
|           within such NOTICE file, excluding those notices that do not | ||||
|           pertain to any part of the Derivative Works, in at least one | ||||
|           of the following places: within a NOTICE text file distributed | ||||
|           as part of the Derivative Works; within the Source form or | ||||
|           documentation, if provided along with the Derivative Works; or, | ||||
|           within a display generated by the Derivative Works, if and | ||||
|           wherever such third-party notices normally appear. The contents | ||||
|           of the NOTICE file are for informational purposes only and | ||||
|           do not modify the License. You may add Your own attribution | ||||
|           notices within Derivative Works that You distribute, alongside | ||||
|           or as an addendum to the NOTICE text from the Work, provided | ||||
|           that such additional attribution notices cannot be construed | ||||
|           as modifying the License. | ||||
|  | ||||
|       You may add Your own copyright statement to Your modifications and | ||||
|       may provide additional or different license terms and conditions | ||||
|       for use, reproduction, or distribution of Your modifications, or | ||||
|       for any such Derivative Works as a whole, provided Your use, | ||||
|       reproduction, and distribution of the Work otherwise complies with | ||||
|       the conditions stated in this License. | ||||
|  | ||||
|    5. Submission of Contributions. Unless You explicitly state otherwise, | ||||
|       any Contribution intentionally submitted for inclusion in the Work | ||||
|       by You to the Licensor shall be under the terms and conditions of | ||||
|       this License, without any additional terms or conditions. | ||||
|       Notwithstanding the above, nothing herein shall supersede or modify | ||||
|       the terms of any separate license agreement you may have executed | ||||
|       with Licensor regarding such Contributions. | ||||
|  | ||||
|    6. Trademarks. This License does not grant permission to use the trade | ||||
|       names, trademarks, service marks, or product names of the Licensor, | ||||
|       except as required for reasonable and customary use in describing the | ||||
|       origin of the Work and reproducing the content of the NOTICE file. | ||||
|  | ||||
|    7. Disclaimer of Warranty. Unless required by applicable law or | ||||
|       agreed to in writing, Licensor provides the Work (and each | ||||
|       Contributor provides its Contributions) on an "AS IS" BASIS, | ||||
|       WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or | ||||
|       implied, including, without limitation, any warranties or conditions | ||||
|       of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A | ||||
|       PARTICULAR PURPOSE. You are solely responsible for determining the | ||||
|       appropriateness of using or redistributing the Work and assume any | ||||
|       risks associated with Your exercise of permissions under this License. | ||||
|  | ||||
|    8. Limitation of Liability. In no event and under no legal theory, | ||||
|       whether in tort (including negligence), contract, or otherwise, | ||||
|       unless required by applicable law (such as deliberate and grossly | ||||
|       negligent acts) or agreed to in writing, shall any Contributor be | ||||
|       liable to You for damages, including any direct, indirect, special, | ||||
|       incidental, or consequential damages of any character arising as a | ||||
|       result of this License or out of the use or inability to use the | ||||
|       Work (including but not limited to damages for loss of goodwill, | ||||
|       work stoppage, computer failure or malfunction, or any and all | ||||
|       other commercial damages or losses), even if such Contributor | ||||
|       has been advised of the possibility of such damages. | ||||
|  | ||||
|    9. Accepting Warranty or Additional Liability. While redistributing | ||||
|       the Work or Derivative Works thereof, You may choose to offer, | ||||
|       and charge a fee for, acceptance of support, warranty, indemnity, | ||||
|       or other liability obligations and/or rights consistent with this | ||||
|       License. However, in accepting such obligations, You may act only | ||||
|       on Your own behalf and on Your sole responsibility, not on behalf | ||||
|       of any other Contributor, and only if You agree to indemnify, | ||||
|       defend, and hold each Contributor harmless for any liability | ||||
|       incurred by, or claims asserted against, such Contributor by reason | ||||
|       of your accepting any such warranty or additional liability. | ||||
|  | ||||
|    END OF TERMS AND CONDITIONS | ||||
|  | ||||
|    APPENDIX: How to apply the Apache License to your work. | ||||
|  | ||||
|       To apply the Apache License to your work, attach the following | ||||
|       boilerplate notice, with the fields enclosed by brackets "{}" | ||||
|       replaced with your own identifying information. (Don't include | ||||
|       the brackets!)  The text should be enclosed in the appropriate | ||||
|       comment syntax for the file format. We also recommend that a | ||||
|       file or class name and description of purpose be included on the | ||||
|       same "printed page" as the copyright notice for easier | ||||
|       identification within third-party archives. | ||||
|  | ||||
|    Copyright 2014 Sublime HQ Pty Ltd | ||||
|  | ||||
|    Licensed under the Apache License, Version 2.0 (the "License"); | ||||
|    you may not use this file except in compliance with the License. | ||||
|    You may obtain a copy of the License at | ||||
|  | ||||
|        http://www.apache.org/licenses/LICENSE-2.0 | ||||
|  | ||||
|    Unless required by applicable law or agreed to in writing, software | ||||
|    distributed under the License is distributed on an "AS IS" BASIS, | ||||
|    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||||
|    See the License for the specific language governing permissions and | ||||
|    limitations under the License. | ||||
							
								
								
									
										26
									
								
								vendor/licenses/grammar/shaders-tmLanguage.txt
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										26
									
								
								vendor/licenses/grammar/shaders-tmLanguage.txt
									
									
									
									
										vendored
									
									
										Normal file
									
								
							| @@ -0,0 +1,26 @@ | ||||
| --- | ||||
| type: grammar | ||||
| name: shaders-tmLanguage | ||||
| license: mit | ||||
| --- | ||||
| MIT License | ||||
|  | ||||
| Copyright (c) 2017 Tim Jones | ||||
|  | ||||
| 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. | ||||
		Reference in New Issue
	
	Block a user