Compare commits
725 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 39eecd136f | |||
| 260cfe6dc9 | |||
| 455af41a19 | |||
| f3c8aa2790 | |||
| e2312e3efd | |||
| a460ce4665 | |||
| d06431e530 | |||
| 34ec0d9629 | |||
| 4ac23c0ac5 | |||
| 507cf31ff9 | |||
| 91414918d7 | |||
| 52c21fe51d | |||
| 2f0a50b526 | |||
| 4a80a2e8bc | |||
| 446fac84d9 | |||
| 43f72066e1 | |||
| a909ed1a5c | |||
| 1c6edd416b | |||
| 8bda5ec735 | |||
| 23395ce07d | |||
| c81c9e7cf4 | |||
| 344b4bcb95 | |||
| 34ba294f76 | |||
| 50ecc370b9 | |||
| 622c421696 | |||
| db1180f3b3 | |||
| ca5b27bd0b | |||
| 3d158f629b | |||
| 8aecf46ad2 | |||
| 2072641537 | |||
| 63154c3d1a | |||
| 37cb9ad436 | |||
| 5a3504abdc | |||
| 0dfc1dfebf | |||
| e9c406b246 | |||
| 79b6d55792 | |||
| 8f94b5b277 | |||
| b11120be0a | |||
| bfba95ce46 | |||
| 310f80e78e | |||
| acfda1022d | |||
| 04d4d93e5b | |||
| 8348365df9 | |||
| 16bcdcb61d | |||
| adcfa74327 | |||
| d641901be6 | |||
| eae0a1121f | |||
| 173c9063e7 | |||
| b461551b81 | |||
| 63492a0261 | |||
| adb0e1746b | |||
| 3be79cd6a1 | |||
| e4c6e01791 | |||
| fb76d96009 | |||
| f322c4f3c3 | |||
| 081f6ec7f2 | |||
| 9bb6a30417 | |||
| 97e97d1eb7 | |||
| 1ab4e44443 | |||
| 99eeec358c | |||
| ce8a7525cc | |||
| 5df2e5ce29 | |||
| ef03dfc4a4 | |||
| 4ff9c027b0 | |||
| 20b8ece444 | |||
| 6406e3b01d | |||
| 234053fc9a | |||
| a277bcf0f7 | |||
| 7985416d39 | |||
| dc3013e848 | |||
| 0f2926db38 | |||
| bd59335eba | |||
| 6aa111b333 | |||
| 42b5ce99fb | |||
| 2cb1989d12 | |||
| 1137d91abd | |||
| 288e4e33c3 | |||
| d98c5f03a4 | |||
| 8d20b04f1c | |||
| 56c3666fe5 | |||
| cd21216ff7 | |||
| 3ffdf380c5 | |||
| db5e0ffe12 | |||
| 92e4801d88 | |||
| 6a92e9111f | |||
| ba6d37756e | |||
| 683bd92f56 | |||
| 7700e2df09 | |||
| 3fb809e412 | |||
| 52ea4110d3 | |||
| a3a7afd3aa | |||
| 20bc37fbc8 | |||
| 7761b6c3b0 | |||
| b77e14beea | |||
| a1f461e429 | |||
| 13587193a5 | |||
| a1ff35850c | |||
| 95b3e1ce6c | |||
| b78b12976a | |||
| a31c082de6 | |||
| 5afd54514d | |||
| 72b96ef57a | |||
| 90975db5f9 | |||
| 25bc531802 | |||
| 4e1b36c216 | |||
| d4fa331308 | |||
| a801df719e | |||
| cb74999b17 | |||
| 2764536e8f | |||
| 8ccc0547a8 | |||
| dd14e0c44d | |||
| 7e24590fa3 | |||
| 8b6360338d | |||
| d91cf16796 | |||
| f31c5a3924 | |||
| 16ccac91d0 | |||
| 91b080e6e6 | |||
| feeb19787c | |||
| 98c2db7f9c | |||
| 06aa52efff | |||
| fabc6ab5b0 | |||
| 93c7251f5f | |||
| e1def1b8fe | |||
| e5cab951f4 | |||
| f7eab8d8fe | |||
| 495d40d802 | |||
| d28ae2126e | |||
| 8955cfb646 | |||
| 776972ed9c | |||
| 1358b3ca9b | |||
| e020b8993e | |||
| b2b896f949 | |||
| 3c5827b6f5 | |||
| 0e03644dad | |||
| 112024271b | |||
| bca0a1f786 | |||
| 959f2bbb2d | |||
| 6a47c0d75d | |||
| b0248b7894 | |||
| 6fd41e7f59 | |||
| 3297bbd188 | |||
| 8863836cd4 | |||
| b8fb0c4573 | |||
| 17b700a339 | |||
| 811b20e3b9 | |||
| 5ded3d3e73 | |||
| 986647a968 | |||
| 7b51243be5 | |||
| 798fb18542 | |||
| 99d601a048 | |||
| a6e9174a27 | |||
| dec8a0eb72 | |||
| 98776487a0 | |||
| b3ef5e0852 | |||
| 04efdd5bfa | |||
| 9f5d76e16b | |||
| 525be5b7d4 | |||
| 042e0f1f0a | |||
| 03872983a4 | |||
| 62f79e820f | |||
| e5c26e92cc | |||
| 4bcb307abc | |||
| 0e729e1dd5 | |||
| 9bb184d181 | |||
| a7a053f5be | |||
| 9630159444 | |||
| e3be5d6efa | |||
| c2173c1298 | |||
| 0b94e8a8bf | |||
| 983374c574 | |||
| 05d3ed0d9b | |||
| 1b25f80cd2 | |||
| 6cdbda7cf1 | |||
| c9e6cf9be0 | |||
| c7ed8a33af | |||
| 6988667e5e | |||
| e57cf13d5d | |||
| e4e5677fbd | |||
| 8b6b428271 | |||
| 8f0b482596 | |||
| 6428ed5bb5 | |||
| bc41ad8aa8 | |||
| 6858caf251 | |||
| 20604e7fc4 | |||
| b7b06d8477 | |||
| de9777d819 | |||
| 1b06f33f30 | |||
| ca6e266869 | |||
| 23c4ae522a | |||
| 3112f8e910 | |||
| 21ab82906e | |||
| 1dd206ef85 | |||
| da5db4b1b3 | |||
| 3694390c90 | |||
| 36a3c81177 | |||
| b0e7d548d0 | |||
| e4bb838795 | |||
| 0ea535035a | |||
| e9aba90f7f | |||
| f50b0cb393 | |||
| 8b3bec7e07 | |||
| 6752337629 | |||
| 48ad7486d9 | |||
| 341b834229 | |||
| 7a668cdd7d | |||
| 5a674f3bb9 | |||
| e94b37e20e | |||
| f5ebcbacf8 | |||
| 0812af49bd | |||
| c3ae6ed78e | |||
| c3a2691115 | |||
| 6976d6d8d8 | |||
| b75c0d8d05 | |||
| df6fade6e6 | |||
| 983b059812 | |||
| 25e8c5927c | |||
| 6628b4f1e5 | |||
| 6e18b50a5b | |||
| 77419cf19f | |||
| 193153c3d3 | |||
| 6a0686d434 | |||
| 08c9a5e9e7 | |||
| a72c12bd70 | |||
| 73e38658c4 | |||
| b641181b93 | |||
| 7ffb2d3c17 | |||
| 023b777a56 | |||
| 0c9480de8c | |||
| 0bc275461c | |||
| 0b5ecc64f0 | |||
| b183eae7ae | |||
| 7ddbc9aa35 | |||
| b2a937d425 | |||
| 4473b81cda | |||
| 98528be311 | |||
| 9190d4c3ad | |||
| d9ec9951e2 | |||
| fedafdc677 | |||
| 26c36bb4d1 | |||
| c7a2028ab3 | |||
| 596af70101 | |||
| 96c73a0672 | |||
| 1537651c8c | |||
| d59aeb4e0b | |||
| 551a33db56 | |||
| cd91640146 | |||
| ab5824ee12 | |||
| 5c50723535 | |||
| 546a277d65 | |||
| a5ff651a59 | |||
| ccd47ec904 | |||
| 2e23a3cdbc | |||
| ca7f4a387c | |||
| 898a3fd3b9 | |||
| 9473371343 | |||
| e5275590db | |||
| 78297d252d | |||
| e5e0884eaf | |||
| 551d1c20cf | |||
| f5aa207960 | |||
| 4412fe238f | |||
| 8088284f66 | |||
| 25f1bbaad1 | |||
| bd7b217729 | |||
| 50557a6cd3 | |||
| 1c13a4f45d | |||
| 1a98c0ee34 | |||
| b837fc3116 | |||
| aff74ec87b | |||
| 077ee37942 | |||
| 0efef2385f | |||
| 7da22e6685 | |||
| 92bdd7627f | |||
| 39ebb06baf | |||
| 9cf6b197ab | |||
| 4971ef12d4 | |||
| 7c792f4cc9 | |||
| 4daafd3dbe | |||
| fe11265fdc | |||
| 75292a6cb5 | |||
| 4ff6c85792 | |||
| e26bc2370b | |||
| 33713deeb8 | |||
| 17715fa366 | |||
| 96288d02d3 | |||
| 8be98e4fdf | |||
| cf83b4f445 | |||
| 15bfea8339 | |||
| 9b90c32f31 | |||
| f4bf744516 | |||
| 0d96995fcc | |||
| 2a85a634f8 | |||
| 00d2b2c4cf | |||
| e688f07023 | |||
| 8e2f7d37e4 | |||
| f5bc3ed9b4 | |||
| 11d60af3dc | |||
| 865f6065e7 | |||
| 91c0b364af | |||
| fce07f55e5 | |||
| c8768d12f2 | |||
| af6342d6fb | |||
| a179757fad | |||
| 35eada68c4 | |||
| bfad2a4f4a | |||
| 54e816552f | |||
| 4fc734665e | |||
| b8736e65b0 | |||
| b9bed7d9da | |||
| b2fc39d2dd | |||
| 7c0731edb2 | |||
| 8fe781fbe7 | |||
| 23932a26ff | |||
| 3ca4ca463c | |||
| 395f3ec638 | |||
| 964a901bd8 | |||
| a995ee17ee | |||
| 794d1c1ebe | |||
| 662fb282c1 | |||
| ffb6b2fb56 | |||
| 941c1c35f1 | |||
| 29a05984fe | |||
| 4038aabffa | |||
| 773efd0812 | |||
| 80881949fc | |||
| 2c8d87e064 | |||
| 33c67ce785 | |||
| ad4296d966 | |||
| 469b14a525 | |||
| 1caf0b6bee | |||
| 9f716dd590 | |||
| 914a934b6f | |||
| a4ada8ba9c | |||
| 40c974ab14 | |||
| 06f002b161 | |||
| 8226ff8b8e | |||
| d67e999dfb | |||
| a8e03b3a90 | |||
| 6f3e26c404 | |||
| 1c75ea613d | |||
| c8e1db2050 | |||
| 74ed28665d | |||
| 4ad0ca130d | |||
| b51dd3010d | |||
| 6e6f31943c | |||
| 66fee7e22a | |||
| beea571660 | |||
| 0c8a9a0e1a | |||
| fd83d3724a | |||
| 2fcfd75a14 | |||
| 2d40507547 | |||
| ecf9304811 | |||
| b9ab88776b | |||
| 00bf218304 | |||
| 95fbf168d1 | |||
| 51a27c0f1a | |||
| f02811f0bb | |||
| bcf78ebb18 | |||
| 3050dd1b47 | |||
| 1efdb4745a | |||
| d73f7dff45 | |||
| f047ad2628 | |||
| 049d3def80 | |||
| 00778aa239 | |||
| 6b123a0419 | |||
| 4079eea6b3 | |||
| d277ac2eb8 | |||
| 9deb123d04 | |||
| 1c2d2e8ba0 | |||
| 144bcc84ab | |||
| 693021c449 | |||
| dc818e1165 | |||
| e51174bf13 | |||
| 7f3f3dd3eb | |||
| d077966ff1 | |||
| 0df4ff800a | |||
| 6208b76afa | |||
| 70dac5ae82 | |||
| aafbd94439 | |||
| e732f8e579 | |||
| 9f67da6252 | |||
| b3a3c6a72e | |||
| e8cdabe129 | |||
| 3af71bee75 | |||
| f2724b2bbc | |||
| 38500669f6 | |||
| 862c9d8bb2 | |||
| 240d5896ec | |||
| 64ef084b91 | |||
| 8b27c3f064 | |||
| 8366622bed | |||
| d3de0066b0 | |||
| b7e5133b2e | |||
| 42c97c5db5 | |||
| e1f4f23f78 | |||
| 630280c7fb | |||
| 496a67c10e | |||
| 7dcfe5e03e | |||
| 9e83b8355e | |||
| 03726f7fbd | |||
| 75893ae9e7 | |||
| d9ca245917 | |||
| 3259aabdf3 | |||
| befeeb3689 | |||
| 79577c5d31 | |||
| b71d7c3f3c | |||
| fa4c7b7f1d | |||
| 652b83eb22 | |||
| 20cf7d5e3a | |||
| ded2518756 | |||
| b366f0352a | |||
| 76c2491a31 | |||
| ef3df93afe | |||
| 106f90aafa | |||
| 86e8088b38 | |||
| a654bdfed9 | |||
| 2c22c57e58 | |||
| a4dfa4d061 | |||
| bc0d8c4eea | |||
| 9b84fcad76 | |||
| f33ce173c9 | |||
| 181fc567d8 | |||
| 94207f8fb6 | |||
| 35a21532b7 | |||
| 1c97a6057b | |||
| 658a865c5b | |||
| f8cf28a788 | |||
| 4dd10fd964 | |||
| 26119c09d1 | |||
| 927ebd9986 | |||
| f5536ab43c | |||
| 9e6a9b9922 | |||
| bfa66a90c2 | |||
| cdd1227a30 | |||
| 19ecdb54bf | |||
| 30aa3eff4c | |||
| 8d39bd8abf | |||
| 472d076cca | |||
| 1ae0be13c2 | |||
| 159efdd429 | |||
| 4755a35b7d | |||
| b2f8b0b875 | |||
| 24cd70058d | |||
| e46ab43422 | |||
| 8a62a8c7f0 | |||
| b6c2f8b854 | |||
| 00ee090f4f | |||
| 544001f5a3 | |||
| 7175d0d0e3 | |||
| 010d9b6853 | |||
| 122ab074ca | |||
| e22bf9ac78 | |||
| 324cb6b358 | |||
| 80a2176e20 | |||
| 681affef59 | |||
| 0ca8b1df20 | |||
| 20fb626b78 | |||
| 7ea2c7f36e | |||
| 912cbdd468 | |||
| 0202663e93 | |||
| 159bbf11ac | |||
| 9d2cc8341c | |||
| 38520a1a73 | |||
| 470eb37d29 | |||
| 4baf25b3ce | |||
| eb193686a5 | |||
| 4bebe7830b | |||
| 146cbf7eaa | |||
| b8e356191f | |||
| f48244ce5e | |||
| ebba426c0c | |||
| aa11dfc162 | |||
| c6110e8b08 | |||
| 290b5049c2 | |||
| f8a07dd9fe | |||
| 6f39f10827 | |||
| c3a654b7c8 | |||
| e7293daf2a | |||
| c71d414a95 | |||
| 06d4e18cda | |||
| 966e01cf26 | |||
| 67afd9dc63 | |||
| 4175860af1 | |||
| 6fb90bda9a | |||
| 770dd2dcfd | |||
| 0ff7bba2e3 | |||
| 82b0929e4e | |||
| 7d2c6eeef8 | |||
| 6d8c1950a0 | |||
| 1a5ea22079 | |||
| 4f9eb2c6e4 | |||
| 43769fb676 | |||
| 170cd96646 | |||
| 1d18e60ef7 | |||
| ea8016c4c8 | |||
| c3d5e33e18 | |||
| 2f6b6fb7a1 | |||
| ea2518fcea | |||
| 7e67e525a5 | |||
| 0e001084ff | |||
| 85e3203918 | |||
| f95bc42cee | |||
| 9080d2c53c | |||
| 728f7e2a85 | |||
| 5f704065a7 | |||
| 64631bf2e6 | |||
| aa35b243f8 | |||
| 1cc9c9ca9d | |||
| dc48aadd26 | |||
| ebce2f7253 | |||
| d0e50fdcd0 | |||
| d88167318d | |||
| 0a75a3db6e | |||
| b643f0d322 | |||
| 01dd588a28 | |||
| 3d6dc3fe31 | |||
| 0c81e9fd25 | |||
| 5df80e1854 | |||
| ba9fb82f18 | |||
| b497f3e47f | |||
| 39b634e50a | |||
| cf28c1a276 | |||
| 92e41ac904 | |||
| d33cedda16 | |||
| 6838c97945 | |||
| f827a8e050 | |||
| a844138060 | |||
| 8ae9e94ecb | |||
| 1bd451d082 | |||
| c11a7d676f | |||
| 0827e88e21 | |||
| 1363cbd6b4 | |||
| 44a96a4c14 | |||
| 1cf10ab810 | |||
| ed3a33a063 | |||
| a268c29fb0 | |||
| adb286389c | |||
| 94533e5706 | |||
| 99d2c46a16 | |||
| 929ec6ba5a | |||
| 39ff3332a3 | |||
| 4c92a3ccc7 | |||
| dc0b856e9c | |||
| bb281f85e7 | |||
| 496e08a605 | |||
| 548a1348d9 | |||
| 9845570be8 | |||
| 35d35e6a7e | |||
| 5abf593e6b | |||
| 9efe60f294 | |||
| 8553b56e97 | |||
| a8f7e9cfde | |||
| 7b8a16b238 | |||
| d2695b04a7 | |||
| 6f3b8622ad | |||
| 97ac7634df | |||
| ef3846a7a6 | |||
| 93985804a9 | |||
| 533d9b7670 | |||
| 0d6fc2dce5 | |||
| addb1ae37d | |||
| f13852c179 | |||
| 5298672411 | |||
| 058d462fa7 | |||
| f91eb0e9ec | |||
| 861636c625 | |||
| e7423168fb | |||
| 4bcf6c17c8 | |||
| d506b8a9df | |||
| e0cf496f3c | |||
| a5221f320a | |||
| 18a2e4fbfc | |||
| 32d3cbb3aa | |||
| acc53ce6ad | |||
| 0f6d37ead5 | |||
| 11695ca6e2 | |||
| cce084ee89 | |||
| d935c245c0 | |||
| b871b98a57 | |||
| 1cb6bd4944 | |||
| 3abb3fefe6 | |||
| 8ed682941a | |||
| 44ce9c8288 | |||
| 2ff1b09ab7 | |||
| 976cd036da | |||
| 21d6db382d | |||
| fc7d2d2737 | |||
| c77b607e61 | |||
| ec22d2276e | |||
| 344dffbc54 | |||
| 7db5f361b0 | |||
| d494a69ef6 | |||
| 91212d9440 | |||
| b661887072 | |||
| 60b7b003fd | |||
| 6ba5404406 | |||
| 2b68136a20 | |||
| dc49b4d952 | |||
| 96f2e3bef5 | |||
| 70ce425e6a | |||
| 9e492c358c | |||
| 92c7ce5bec | |||
| 618356e481 | |||
| 1f4aa47193 | |||
| 528cedaa0c | |||
| 1622182737 | |||
| 36efe6c1a2 | |||
| 5081982e30 | |||
| 97d79eec80 | |||
| e4aeae0c73 | |||
| 7202bfafcd | |||
| 4cef752985 | |||
| d38f6ff401 | |||
| 8f6dac9536 | |||
| de5b8dc781 | |||
| 41834e6f4a | |||
| dbb42b5c85 | |||
| f012374f12 | |||
| 14e0b9c352 | |||
| 9ea52d818b | |||
| d518a64d93 | |||
| fe0af2c073 | |||
| 1f5e42e882 | |||
| d193c3a25c | |||
| 4da1cc3b81 | |||
| 6de08216e7 | |||
| 3c6e8ce044 | |||
| e51024ed54 | |||
| 04f1ebd470 | |||
| 2e63ab734a | |||
| 6333d65b76 | |||
| 1ce5d216c7 | |||
| 28c166939e | |||
| 14638f4a60 | |||
| 0c1fbdd242 | |||
| 33f7f26558 | |||
| e27eed3ca4 | |||
| 6cbbd96647 | |||
| d0cb69348e | |||
| f15f8df2b4 | |||
| e7662ebc31 | |||
| 8ceed4faf3 | |||
| 6903b5ec4c | |||
| 48e1f5605e | |||
| c5a3d8fc5f | |||
| c61149213b | |||
| ad7200e2c2 | |||
| bea74c0f56 | |||
| bacc3b7e0e | |||
| 8a1eb1625c | |||
| ed27e0ea6a | |||
| f81ff3beb0 | |||
| 720012eab6 | |||
| 3adfe5bda9 | |||
| dc0467879d | |||
| 528d7f9568 | |||
| 636ce70e47 | |||
| 5f5ee0f880 | |||
| 46b7cf7464 | |||
| 860edee65b | |||
| ebd0fbba8f | |||
| 093416f60f | |||
| 0400dc9c2a | |||
| 71fc3f4fa0 | |||
| 8caf1802e0 | |||
| 91b602263b | |||
| 0934b76b72 | |||
| 571bee7b2f | |||
| 11055132bf | |||
| 0898b1240b | |||
| 8dc09e6dab | |||
| 799353c75d | |||
| ffac747e84 | |||
| 998340de7f | |||
| 559313652e | |||
| a69251ab55 | |||
| 7e5248a33f | |||
| c210ff5eae | |||
| 9efb0d5ee9 | |||
| 0e622f7b5b | |||
| 071be60927 | |||
| a25aa5b577 | |||
| df9c720d08 | |||
| 4fe141f794 | |||
| f3b1d0b723 | |||
| 288225b080 | |||
| e967abcd30 | |||
| 2c3cd8126c | |||
| 41385f0afc | |||
| 500b0f6cdb | |||
| 40b27280ab | |||
| b73c64e2fb | |||
| 2f5d42ec72 | |||
| 25d731e9b0 | |||
| 15da7cc3dc | |||
| 34a6da24c1 | |||
| ebaa0f5985 | |||
| bb15d414c6 | |||
| f056036a4a | |||
| a055762027 | |||
| 82d38e4453 | |||
| 6a743f0b5b | |||
| 31f6f76291 | |||
| a2b5a5ed5f | |||
| 1d41e8a975 | |||
| 01182dfbb8 | |||
| e17f85cc5b | |||
| d7dc14dc0c | |||
| 578fa019b3 | |||
| 3c9096efb4 | |||
| 59273354b5 | |||
| f67204794e | |||
| b6389eedda | |||
| a6339d30d1 | |||
| 351fe4b79c | |||
| d19504a179 | |||
| e5e871fe1a | |||
| 90fa884f94 | |||
| 80b9018f29 | |||
| f6ac226c8b | |||
| 2d22380873 | |||
| 7c49d9986f | |||
| 209f4f3e0f | |||
| 5d68c763e2 | |||
| 3ef529806f |
@@ -1,15 +0,0 @@
|
||||
// This is an incomplete TODO list of checks we want to start enforcing
|
||||
//
|
||||
// The goal is to enable these checks one by one by moving them to .jscs.json along with commits
|
||||
// that correct the existing code base issues and make the new check pass.
|
||||
|
||||
{
|
||||
"validateParameterSeparator": ", ", // Re-assert this rule when JSCS allows multiple spaces
|
||||
"requireCurlyBraces": ["if", "else", "for", "while", "do", "try", "catch"],
|
||||
"disallowImplicitTypeConversion": ["string"],
|
||||
"disallowMultipleLineBreaks": true,
|
||||
"validateJSDoc": {
|
||||
"checkParamNames": true,
|
||||
"requireParamTypes": true
|
||||
}
|
||||
}
|
||||
+19
-23
@@ -1,7 +1,7 @@
|
||||
language: node_js
|
||||
sudo: false
|
||||
node_js:
|
||||
- '0.10'
|
||||
- '4.2'
|
||||
|
||||
cache:
|
||||
directories:
|
||||
@@ -15,28 +15,26 @@ branches:
|
||||
|
||||
env:
|
||||
matrix:
|
||||
- JOB=ci-checks
|
||||
- JOB=unit BROWSER_PROVIDER=saucelabs
|
||||
- JOB=docs-e2e BROWSER_PROVIDER=saucelabs
|
||||
- JOB=e2e TEST_TARGET=jqlite BROWSER_PROVIDER=saucelabs
|
||||
- JOB=e2e TEST_TARGET=jquery BROWSER_PROVIDER=saucelabs
|
||||
- JOB=unit BROWSER_PROVIDER=browserstack
|
||||
- JOB=docs-e2e BROWSER_PROVIDER=browserstack
|
||||
- JOB=e2e TEST_TARGET=jqlite BROWSER_PROVIDER=browserstack
|
||||
- JOB=e2e TEST_TARGET=jquery BROWSER_PROVIDER=browserstack
|
||||
global:
|
||||
- CXX=g++-4.8 # node 4 likes the G++ v4.8 compiler
|
||||
- SAUCE_USERNAME=angular-ci
|
||||
- SAUCE_ACCESS_KEY=9b988f434ff8-fbca-8aa4-4ae3-35442987
|
||||
- BROWSER_STACK_USERNAME=VojtaJina
|
||||
- BROWSER_STACK_ACCESS_KEY=QCQJ1ZpWXpBkSwEdD8ev
|
||||
- LOGS_DIR=/tmp/angular-build/logs
|
||||
- BROWSER_PROVIDER_READY_FILE=/tmp/browsersprovider-tunnel-ready
|
||||
|
||||
matrix:
|
||||
allow_failures:
|
||||
- env: "JOB=unit BROWSER_PROVIDER=browserstack"
|
||||
- env: "JOB=docs-e2e BROWSER_PROVIDER=browserstack"
|
||||
- env: "JOB=e2e TEST_TARGET=jqlite BROWSER_PROVIDER=browserstack"
|
||||
- env: "JOB=e2e TEST_TARGET=jquery BROWSER_PROVIDER=browserstack"
|
||||
# node 4 likes the G++ v4.8 compiler
|
||||
# see https://docs.travis-ci.com/user/languages/javascript-with-nodejs#Node.js-v4-(or-io.js-v3)-compiler-requirements
|
||||
addons:
|
||||
apt:
|
||||
sources:
|
||||
- ubuntu-toolchain-r-test
|
||||
packages:
|
||||
- g++-4.8
|
||||
|
||||
install:
|
||||
# Check the size of caches
|
||||
@@ -46,27 +44,25 @@ install:
|
||||
- npm config set spin false
|
||||
# Log HTTP requests
|
||||
- npm config set loglevel http
|
||||
- npm install -g npm@2.5
|
||||
# Instal npm dependecies and ensure that npm cache is not stale
|
||||
- scripts/npm/install-dependencies.sh
|
||||
#- npm install -g npm@2.5
|
||||
# Install npm dependencies and ensure that npm cache is not stale
|
||||
- npm install
|
||||
|
||||
before_script:
|
||||
- mkdir -p $LOGS_DIR
|
||||
- ./scripts/travis/start_browser_provider.sh
|
||||
- npm install -g grunt-cli
|
||||
- grunt package
|
||||
- ./scripts/travis/wait_for_browser_provider.sh
|
||||
- ./scripts/travis/before_build.sh
|
||||
|
||||
script:
|
||||
- ./scripts/travis/build.sh
|
||||
|
||||
after_script:
|
||||
- ./scripts/travis/tear_down_browser_provider.sh
|
||||
- ./scripts/travis/print_logs.sh
|
||||
|
||||
notifications:
|
||||
webhooks:
|
||||
urls:
|
||||
- https://webhooks.gitter.im/e/d2120f3f2bb39a4531b2
|
||||
on_success: change # options: [always|never|change] default: always
|
||||
- http://104.197.9.155:8484/hubot/travis/activity #hubot-server
|
||||
on_success: always # options: [always|never|change] default: always
|
||||
on_failure: always # options: [always|never|change] default: always
|
||||
on_start: false # default: false
|
||||
on_start: always # default: false
|
||||
|
||||
+1860
-58
File diff suppressed because it is too large
Load Diff
+21
-6
@@ -19,7 +19,7 @@ Help us keep Angular open and inclusive. Please read and follow our [Code of Con
|
||||
## <a name="question"></a> Got a Question or Problem?
|
||||
|
||||
If you have questions about how to use AngularJS, please direct these to the [Google Group][groups]
|
||||
discussion list or [StackOverflow][stackoverflow]. We are also available on [IRC][irc].
|
||||
discussion list or [StackOverflow][stackoverflow]. We are also available on [IRC][irc] and [Gitter][gitter].
|
||||
|
||||
## <a name="issue"></a> Found an Issue?
|
||||
If you find a bug in the source code or a mistake in the documentation, you can help us by
|
||||
@@ -71,7 +71,7 @@ chances of your issue being dealt with quickly:
|
||||
* **Angular Version(s)** - is it a regression?
|
||||
* **Browsers and Operating System** - is this a problem with all browsers or only IE8?
|
||||
* **Reproduce the Error** - provide a live example (using [Plunker][plunker] or
|
||||
[JSFiddle][jsfiddle]) or a unambiguous set of steps.
|
||||
[JSFiddle][jsfiddle]) or an unambiguous set of steps.
|
||||
* **Related Issues** - has a similar issue been reported before?
|
||||
* **Suggest a Fix** - if you can't fix the bug yourself, perhaps you can point to what might be
|
||||
causing the problem (line of code or commit)
|
||||
@@ -123,13 +123,19 @@ Before you submit your pull request consider the following guidelines:
|
||||
* If we suggest changes then:
|
||||
* Make the required updates.
|
||||
* Re-run the Angular test suite to ensure tests are still passing.
|
||||
* Rebase your branch and force push to your GitHub repository (this will update your Pull Request):
|
||||
* Commit your changes to your branch (e.g. `my-fix-branch`).
|
||||
* Push the changes to your GitHub repository (this will update your Pull Request).
|
||||
|
||||
If the PR gets too outdated we may ask you to rebase and force push to update the PR:
|
||||
|
||||
```shell
|
||||
git rebase master -i
|
||||
git push origin my-fix-branch -f
|
||||
```
|
||||
|
||||
*WARNING. Squashing or reverting commits and forced push thereafter may remove GitHub comments
|
||||
on code that were previously made by you and others in your commits.*
|
||||
|
||||
That's it! Thank you for your contribution!
|
||||
|
||||
#### After your pull request is merged
|
||||
@@ -187,6 +193,8 @@ We have very precise rules over how our git commit messages can be formatted. T
|
||||
readable messages** that are easy to follow when looking through the **project history**. But also,
|
||||
we use the git commit messages to **generate the AngularJS change log**.
|
||||
|
||||
The commit message formatting can be added using a typical git workflow or through the use of a CLI wizard ([Commitizen](https://github.com/commitizen/cz-cli)). To use the wizard, run `npm run commit` in your terminal after staging your changes in git.
|
||||
|
||||
### Commit Message Format
|
||||
Each commit message consists of a **header**, a **body** and a **footer**. The header has a special
|
||||
format that includes a **type**, a **scope** and a **subject**:
|
||||
@@ -199,8 +207,13 @@ format that includes a **type**, a **scope** and a **subject**:
|
||||
<footer>
|
||||
```
|
||||
|
||||
The **header** is mandatory and the **scope** of the header is optional.
|
||||
|
||||
Any line of the commit message cannot be longer 100 characters! This allows the message to be easier
|
||||
to read on github as well as in various git tools.
|
||||
to read on GitHub as well as in various git tools.
|
||||
|
||||
### Revert
|
||||
If the commit reverts a previous commit, it should begin with `revert: `, followed by the header of the reverted commit. In the body it should say: `This reverts commit <hash>.`, where the hash is the SHA of the commit being reverted.
|
||||
|
||||
### Type
|
||||
Must be one of the following:
|
||||
@@ -210,7 +223,7 @@ Must be one of the following:
|
||||
* **docs**: Documentation only changes
|
||||
* **style**: Changes that do not affect the meaning of the code (white-space, formatting, missing
|
||||
semi-colons, etc)
|
||||
* **refactor**: A code change that neither fixes a bug or adds a feature
|
||||
* **refactor**: A code change that neither fixes a bug nor adds a feature
|
||||
* **perf**: A code change that improves performance
|
||||
* **test**: Adding missing tests
|
||||
* **chore**: Changes to the build process or auxiliary tools and libraries such as documentation
|
||||
@@ -228,13 +241,14 @@ The subject contains succinct description of the change:
|
||||
* no dot (.) at the end
|
||||
|
||||
### Body
|
||||
Just as in the **subject**, use the imperative, present tense: "change" not "changed" nor "changes"
|
||||
Just as in the **subject**, use the imperative, present tense: "change" not "changed" nor "changes".
|
||||
The body should include the motivation for the change and contrast this with previous behavior.
|
||||
|
||||
### Footer
|
||||
The footer should contain any information about **Breaking Changes** and is also the place to
|
||||
reference GitHub issues that this commit **Closes**.
|
||||
|
||||
**Breaking Changes** should start with the word `BREAKING CHANGE:` with a space or two newlines. The rest of the commit message is then used for this.
|
||||
|
||||
A detailed explanation can be found in this [document][commit-message-format].
|
||||
|
||||
@@ -262,6 +276,7 @@ You can find out more detailed information about contributing in the
|
||||
[corporate-cla]: http://code.google.com/legal/corporate-cla-v1.0.html
|
||||
[dev-doc]: https://docs.angularjs.org/guide
|
||||
[github]: https://github.com/angular/angular.js
|
||||
[gitter]: https://gitter.im/angular/angular.js
|
||||
[groups]: https://groups.google.com/forum/?fromgroups#!forum/angular
|
||||
[individual-cla]: http://code.google.com/legal/individual-cla-v1.0.html
|
||||
[irc]: http://webchat.freenode.net/?channels=angularjs&uio=d4
|
||||
|
||||
+20
-14
@@ -115,7 +115,7 @@ module.exports = function(grunt) {
|
||||
files: { src: 'test/**/*.js' },
|
||||
},
|
||||
ng: {
|
||||
files: { src: files['angularSrc'] },
|
||||
files: { src: files['angularSrc'].concat('!src/angular.bind.js') },
|
||||
},
|
||||
ngAnimate: {
|
||||
files: { src: 'src/ngAnimate/**/*.js' },
|
||||
@@ -156,9 +156,13 @@ module.exports = function(grunt) {
|
||||
},
|
||||
|
||||
jscs: {
|
||||
src: ['src/**/*.js', 'test/**/*.js'],
|
||||
src: [
|
||||
'src/**/*.js',
|
||||
'test/**/*.js',
|
||||
'!src/angular.bind.js' // we ignore this file since contains an early return statement
|
||||
],
|
||||
options: {
|
||||
config: ".jscs.json"
|
||||
config: '.jscsrc'
|
||||
}
|
||||
},
|
||||
|
||||
@@ -227,9 +231,9 @@ module.exports = function(grunt) {
|
||||
dest: 'build/angular-aria.js',
|
||||
src: util.wrap(files['angularModules']['ngAria'], 'module')
|
||||
},
|
||||
"promises-aplus-adapter": {
|
||||
'promises-aplus-adapter': {
|
||||
dest:'tmp/promises-aplus-adapter++.js',
|
||||
src:['src/ng/q.js','lib/promises-aplus/promises-aplus-test-adapter.js']
|
||||
src:['src/ng/q.js', 'lib/promises-aplus/promises-aplus-test-adapter.js']
|
||||
}
|
||||
},
|
||||
|
||||
@@ -249,7 +253,7 @@ module.exports = function(grunt) {
|
||||
},
|
||||
|
||||
|
||||
"ddescribe-iit": {
|
||||
'ddescribe-iit': {
|
||||
files: [
|
||||
'src/**/*.js',
|
||||
'test/**/*.js',
|
||||
@@ -270,7 +274,7 @@ module.exports = function(grunt) {
|
||||
}
|
||||
},
|
||||
|
||||
"merge-conflict": {
|
||||
'merge-conflict': {
|
||||
files: [
|
||||
'src/**/*',
|
||||
'test/**/*',
|
||||
@@ -300,11 +304,11 @@ module.exports = function(grunt) {
|
||||
},
|
||||
|
||||
shell: {
|
||||
"npm-install": {
|
||||
command: path.normalize('scripts/npm/install-dependencies.sh')
|
||||
'npm-install': {
|
||||
command: 'node scripts/npm/check-node-modules.js'
|
||||
},
|
||||
|
||||
"promises-aplus-tests": {
|
||||
'promises-aplus-tests': {
|
||||
options: {
|
||||
stdout: false,
|
||||
stderr: true,
|
||||
@@ -335,8 +339,10 @@ module.exports = function(grunt) {
|
||||
grunt.task.run('shell:npm-install');
|
||||
}
|
||||
|
||||
|
||||
|
||||
//alias tasks
|
||||
grunt.registerTask('test', 'Run unit, docs and e2e tests with Karma', ['jshint', 'jscs', 'package','test:unit','test:promises-aplus', 'tests:docs', 'test:protractor']);
|
||||
grunt.registerTask('test', 'Run unit, docs and e2e tests with Karma', ['jshint', 'jscs', 'package', 'test:unit', 'test:promises-aplus', 'tests:docs', 'test:protractor']);
|
||||
grunt.registerTask('test:jqlite', 'Run the unit tests with Karma' , ['tests:jqlite']);
|
||||
grunt.registerTask('test:jquery', 'Run the jQuery unit tests with Karma', ['tests:jquery']);
|
||||
grunt.registerTask('test:modules', 'Run the Karma module tests with Karma', ['build', 'tests:modules']);
|
||||
@@ -346,11 +352,11 @@ module.exports = function(grunt) {
|
||||
grunt.registerTask('test:travis-protractor', 'Run the end to end tests with Protractor for Travis CI builds', ['connect:testserver', 'protractor:travis']);
|
||||
grunt.registerTask('test:ci-protractor', 'Run the end to end tests with Protractor for Jenkins CI builds', ['webdriver', 'connect:testserver', 'protractor:jenkins']);
|
||||
grunt.registerTask('test:e2e', 'Alias for test:protractor', ['test:protractor']);
|
||||
grunt.registerTask('test:promises-aplus',['build:promises-aplus-adapter','shell:promises-aplus-tests']);
|
||||
grunt.registerTask('test:promises-aplus',['build:promises-aplus-adapter', 'shell:promises-aplus-tests']);
|
||||
|
||||
grunt.registerTask('minify', ['bower','clean', 'build', 'minall']);
|
||||
grunt.registerTask('minify', ['bower', 'clean', 'build', 'minall']);
|
||||
grunt.registerTask('webserver', ['connect:devserver']);
|
||||
grunt.registerTask('package', ['bower','clean', 'buildall', 'minall', 'collect-errors', 'docs', 'copy', 'write', 'compress']);
|
||||
grunt.registerTask('package', ['bower', 'validate-angular-files', 'clean', 'buildall', 'minall', 'collect-errors', 'docs', 'copy', 'write', 'compress']);
|
||||
grunt.registerTask('ci-checks', ['ddescribe-iit', 'merge-conflict', 'jshint', 'jscs']);
|
||||
grunt.registerTask('default', ['package']);
|
||||
};
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
The MIT License
|
||||
|
||||
Copyright (c) 2010-2015 Google, Inc. http://angularjs.org
|
||||
Copyright (c) 2010-2016 Google, Inc. http://angularjs.org
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
+2
-2
@@ -1,8 +1,8 @@
|
||||
Using AngularJS with the Closure Compiler
|
||||
=========================================
|
||||
|
||||
The Closure Compiler project contains externs definitions for AngularJS
|
||||
JavaScript in its `contrib/externs` directory.
|
||||
The Closure Compiler project contains definitions for the AngularJS JavaScript
|
||||
in its `contrib/externs` directory.
|
||||
|
||||
The definitions contain externs for use with the Closure compiler (aka
|
||||
JSCompiler). Passing these files to the --externs parameter of a compiler
|
||||
|
||||
@@ -10,7 +10,7 @@ the browser how to do dependency injection and inversion of control.
|
||||
|
||||
Oh yeah and it helps with server-side communication, taming async callbacks with promises and
|
||||
deferreds. It also makes client-side navigation and deeplinking with hashbang urls or HTML5 pushState a
|
||||
piece of cake. The best of all: it makes development fun!
|
||||
piece of cake. Best of all?? It makes development fun!
|
||||
|
||||
* Web site: http://angularjs.org
|
||||
* Tutorial: http://docs.angularjs.org/tutorial
|
||||
@@ -21,7 +21,7 @@ piece of cake. The best of all: it makes development fun!
|
||||
|
||||
Building AngularJS
|
||||
---------
|
||||
[Once you have your environment setup](http://docs.angularjs.org/misc/contribute) just run:
|
||||
[Once you have your environment set up](http://docs.angularjs.org/misc/contribute) just run:
|
||||
|
||||
grunt package
|
||||
|
||||
|
||||
+1
-1
@@ -20,7 +20,7 @@ The following is done automatically so you don't have to worry about it:
|
||||
This process based on the idea of minimizing user pain
|
||||
[from this blog post](http://www.lostgarden.com/2008/05/improving-bug-triage-with-user-pain.html).
|
||||
|
||||
1. Open the list of [non triaged issues](https://github.com/angular/angular.js/issues?direction=desc&milestone=none&page=1&sort=created&state=open)
|
||||
1. Open the list of [non triaged issues](https://github.com/angular/angular.js/issues?q=is%3Aopen+sort%3Acreated-desc+no%3Amilestone)
|
||||
* Sort by submit date, with the newest issues first
|
||||
* You don't have to do issues in order; feel free to pick and choose issues as you please.
|
||||
* You can triage older issues as well
|
||||
|
||||
Vendored
+14
-8
@@ -14,13 +14,15 @@ var angularFiles = {
|
||||
|
||||
'src/ng/anchorScroll.js',
|
||||
'src/ng/animate.js',
|
||||
'src/ng/asyncCallback.js',
|
||||
'src/ng/animateRunner.js',
|
||||
'src/ng/animateCss.js',
|
||||
'src/ng/browser.js',
|
||||
'src/ng/cacheFactory.js',
|
||||
'src/ng/compile.js',
|
||||
'src/ng/controller.js',
|
||||
'src/ng/document.js',
|
||||
'src/ng/exceptionHandler.js',
|
||||
'src/ng/forceReflow.js',
|
||||
'src/ng/http.js',
|
||||
'src/ng/httpBackend.js',
|
||||
'src/ng/interpolate.js',
|
||||
@@ -32,6 +34,7 @@ var angularFiles = {
|
||||
'src/ng/q.js',
|
||||
'src/ng/raf.js',
|
||||
'src/ng/rootScope.js',
|
||||
'src/ng/rootElement.js',
|
||||
'src/ng/sanitizeUri.js',
|
||||
'src/ng/sce.js',
|
||||
'src/ng/sniffer.js',
|
||||
@@ -76,11 +79,14 @@ var angularFiles = {
|
||||
'src/ng/directive/script.js',
|
||||
'src/ng/directive/select.js',
|
||||
'src/ng/directive/style.js',
|
||||
'src/ng/directive/validators.js'
|
||||
'src/ng/directive/validators.js',
|
||||
'src/angular.bind.js',
|
||||
'src/publishExternalApis.js',
|
||||
'src/ngLocale/angular-locale_en-us.js'
|
||||
],
|
||||
|
||||
'angularLoader': [
|
||||
'stringify.js',
|
||||
'src/stringify.js',
|
||||
'src/minErr.js',
|
||||
'src/loader.js'
|
||||
],
|
||||
@@ -95,8 +101,8 @@ var angularFiles = {
|
||||
'src/ngAnimate/animateJs.js',
|
||||
'src/ngAnimate/animateJsDriver.js',
|
||||
'src/ngAnimate/animateQueue.js',
|
||||
'src/ngAnimate/animateRunner.js',
|
||||
'src/ngAnimate/animation.js',
|
||||
'src/ngAnimate/ngAnimateSwap.js',
|
||||
'src/ngAnimate/module.js'
|
||||
],
|
||||
'ngCookies': [
|
||||
@@ -179,7 +185,6 @@ var angularFiles = {
|
||||
'bower_components/jquery/dist/jquery.js',
|
||||
'test/jquery_remove.js',
|
||||
'@angularSrc',
|
||||
'src/publishExternalApis.js',
|
||||
'@angularSrcModules',
|
||||
'@angularScenario',
|
||||
'@angularTest'
|
||||
@@ -188,7 +193,8 @@ var angularFiles = {
|
||||
'karmaExclude': [
|
||||
'test/jquery_alias.js',
|
||||
'src/angular-bootstrap.js',
|
||||
'src/ngScenario/angular-bootstrap.js'
|
||||
'src/ngScenario/angular-bootstrap.js',
|
||||
'src/angular.bind.js'
|
||||
],
|
||||
|
||||
'karmaScenario': [
|
||||
@@ -215,7 +221,6 @@ var angularFiles = {
|
||||
'bower_components/jquery/dist/jquery.js',
|
||||
'test/jquery_alias.js',
|
||||
'@angularSrc',
|
||||
'src/publishExternalApis.js',
|
||||
'@angularSrcModules',
|
||||
'@angularScenario',
|
||||
'@angularTest'
|
||||
@@ -224,7 +229,8 @@ var angularFiles = {
|
||||
'karmaJqueryExclude': [
|
||||
'src/angular-bootstrap.js',
|
||||
'src/ngScenario/angular-bootstrap.js',
|
||||
'test/jquery_remove.js'
|
||||
'test/jquery_remove.js',
|
||||
'src/angular.bind.js'
|
||||
]
|
||||
};
|
||||
|
||||
|
||||
@@ -8,20 +8,20 @@
|
||||
Large table rendered with AngularJS
|
||||
</p>
|
||||
|
||||
<div>none: <input type="radio" ng-model="benchmarkType" value="none"></div>
|
||||
<div>baseline binding: <input type="radio" ng-model="benchmarkType" value="baselineBinding"></div>
|
||||
<div>baseline interpolation: <input type="radio" ng-model="benchmarkType" value="baselineInterpolation"></div>
|
||||
<div>ngBind: <input type="radio" ng-model="benchmarkType" value="ngBind"></div>
|
||||
<div>ngBindOnce: <input type="radio" ng-model="benchmarkType" value="ngBindOnce"></div>
|
||||
<div>interpolation: <input type="radio" ng-model="benchmarkType" value="interpolation"></div>
|
||||
<div>interpolation + bind-once: <input type="radio" ng-model="benchmarkType" value="bindOnceInterpolation"></div>
|
||||
<div>attribute interpolation: <input type="radio" ng-model="benchmarkType" value="interpolationAttr"></div>
|
||||
<div>ngBind + fnInvocation: <input type="radio" ng-model="benchmarkType" value="ngBindFn"></div>
|
||||
<div>interpolation + fnInvocation: <input type="radio" ng-model="benchmarkType" value="interpolationFn"></div>
|
||||
<div>ngBind + filter: <input type="radio" ng-model="benchmarkType" value="ngBindFilter"></div>
|
||||
<div>interpolation + filter: <input type="radio" ng-model="benchmarkType" value="interpolationFilter"></div>
|
||||
<div>ngModel (const name): <input type="radio" ng-model="benchmarkType" value="ngModelConstName"></div>
|
||||
<div>ngModel (interp name): <input type="radio" ng-model="benchmarkType" value="ngModelInterpName"></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="none">none: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="baselineBinding">baseline binding: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="baselineInterpolation">baseline interpolation: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="ngBind">ngBind: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="ngBindOnce">ngBindOnce: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="interpolation">interpolation: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="bindOnceInterpolation">interpolation + bind-once: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="interpolationAttr">attribute interpolation: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="ngBindFn">ngBind + fnInvocation: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="interpolationFn">interpolation + fnInvocation: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="ngBindFilter">ngBind + filter: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="interpolationFilter">interpolation + filter: </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="ngModelConstName">ngModel (const name): </label></div>
|
||||
<div><label><input type="radio" ng-model="benchmarkType" value="ngModelInterpName">ngModel (interp name): </label></div>
|
||||
|
||||
<ng-switch on="benchmarkType">
|
||||
<baseline-binding-table ng-switch-when="baselineBinding">
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
{
|
||||
"name": "AngularJS",
|
||||
"license": "MIT",
|
||||
"devDependencies": {
|
||||
"jquery": "2.1.1",
|
||||
"closure-compiler": "https://dl.google.com/closure-compiler/compiler-20140814.zip",
|
||||
|
||||
@@ -44,7 +44,7 @@ var noArgs = function (fn) {
|
||||
|
||||
var identity = function (i) { return i; };
|
||||
|
||||
// like Q.all, but runs the comands in series
|
||||
// like Q.all, but runs the commands in series
|
||||
// useful for ensuring env state (like which branch is checked out)
|
||||
var allInSeries = function (fn) {
|
||||
return function (args) {
|
||||
|
||||
@@ -56,7 +56,7 @@ li.doc-example-live {
|
||||
}
|
||||
|
||||
div.syntaxhighlighter {
|
||||
padding-bottom: 1px !important; /* fix to remove unnecessary scrollbars http://is.gd/gSMgC */
|
||||
padding-bottom: 1px !important; /* fix to remove unnecessary scrollbars */
|
||||
}
|
||||
|
||||
/* TABS - tutorial environment navigation */
|
||||
|
||||
@@ -124,7 +124,7 @@ h1,h2,h3,h4,h5,h6 {
|
||||
font-size:1.2em;
|
||||
padding:0;
|
||||
margin:0;
|
||||
border-bottom:1px soild #aaa;
|
||||
border-bottom:1px solid #aaa;
|
||||
margin-bottom:5px;
|
||||
}
|
||||
|
||||
@@ -315,8 +315,13 @@ iframe.example {
|
||||
color:white;
|
||||
}
|
||||
|
||||
.search-results-group .search-results {
|
||||
padding: 0 5px 0;
|
||||
list-style-type: none;
|
||||
}
|
||||
|
||||
.search-results-frame > .search-results-group:first-child > .search-results {
|
||||
border-right:1px solid #050505;
|
||||
border-right:1px solid #222;
|
||||
}
|
||||
|
||||
.search-results-group.col-group-api { width:30%; }
|
||||
@@ -325,10 +330,57 @@ iframe.example {
|
||||
.search-results-group.col-group-misc,
|
||||
.search-results-group.col-group-error { width:15%; float: right; }
|
||||
|
||||
@supports ((column-count: 2) or (-moz-column-count: 2) or (-ms-column-count: 2) or (-webkit-column-count: 2)) {
|
||||
.search-results-group.col-group-api .search-results {
|
||||
-moz-column-count: 2;
|
||||
-ms-column-count: 2;
|
||||
-webkit-column-count: 2;
|
||||
column-count: 2;
|
||||
/* Prevent bullets in the second column from being hidden in Chrome and IE */
|
||||
-webkit-column-gap: 2em;
|
||||
-ms-column-gap: 2em;
|
||||
column-gap: 2em;
|
||||
}
|
||||
}
|
||||
|
||||
.search-results-group .search-result {
|
||||
word-wrap: break-word;
|
||||
-webkit-hyphens: auto;
|
||||
-moz-hyphens: auto;
|
||||
-ms-hyphens: auto;
|
||||
hyphens: auto;
|
||||
-ms-column-break-inside: avoid;
|
||||
-webkit-column-break-inside: avoid;
|
||||
-moz-column-break-inside: avoid; /* Unsupported */
|
||||
column-break-inside: avoid;
|
||||
text-indent: -0.65em; /* Make sure line wrapped words are aligned vertically */
|
||||
}
|
||||
|
||||
@supports (-moz-column-count: 2) {
|
||||
.search-results-group .search-result {
|
||||
/* Prevents column breaks inside words in FF, but has adverse effects in IE11 and Chrome */
|
||||
overflow: hidden;
|
||||
padding-left: 1em; /* In FF the list item bullet is otherwise hidden */
|
||||
margin-left: -1em; /* offset the padding left */
|
||||
}
|
||||
}
|
||||
|
||||
.search-result:before {
|
||||
content: "\002D\00A0"; /* Dash and non-breaking space as List item type */
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.search-results-group.col-group-api .search-result {
|
||||
width:48%;
|
||||
display:inline-block;
|
||||
padding-left: 12px;
|
||||
}
|
||||
|
||||
@supports ((column-count: 2) or (-moz-column-count: 2) or (-ms-column-count: 2) or (-webkit-column-count: 2)) {
|
||||
.search-results-group.col-group-api .search-result {
|
||||
width:auto;
|
||||
display: list-item;
|
||||
}
|
||||
}
|
||||
|
||||
.search-close {
|
||||
@@ -589,6 +641,12 @@ ul.events > li {
|
||||
vertical-align: top;
|
||||
}
|
||||
|
||||
.table > tbody > tr.head > td,
|
||||
.table > tbody > tr.head > th {
|
||||
border-bottom: 2px solid #ddd;
|
||||
padding-top: 50px;
|
||||
}
|
||||
|
||||
@media only screen and (min-width: 769px) and (max-width: 991px) {
|
||||
.main-body-grid {
|
||||
margin-top: 160px;
|
||||
@@ -682,6 +740,11 @@ ul.events > li {
|
||||
padding-bottom:60px;
|
||||
text-align:left;
|
||||
}
|
||||
|
||||
.search-results-frame > .search-results-group:first-child > .search-results {
|
||||
border-right: none;
|
||||
}
|
||||
|
||||
.search-results-group {
|
||||
float:none!important;
|
||||
display:block!important;
|
||||
@@ -689,14 +752,42 @@ ul.events > li {
|
||||
border:0!important;
|
||||
padding:0!important;
|
||||
}
|
||||
|
||||
@supports ((column-count: 2) or (-moz-column-count: 2) or (-ms-column-count: 2) or (-webkit-column-count: 2)) {
|
||||
.search-results-group .search-results {
|
||||
-moz-column-count: 2;
|
||||
-ms-column-count: 2;
|
||||
-webkit-column-count: 2;
|
||||
column-count: 2;
|
||||
}
|
||||
}
|
||||
|
||||
.search-results-group .search-result {
|
||||
display:inline-block!important;
|
||||
padding:0 5px;
|
||||
width:auto!important;
|
||||
text-indent: initial;
|
||||
margin-left: 0;
|
||||
}
|
||||
|
||||
.search-results-group .search-result:after {
|
||||
content:", ";
|
||||
}
|
||||
|
||||
.search-results-group .search-result:before {
|
||||
content: "";
|
||||
}
|
||||
|
||||
@supports ((column-count: 2) or (-moz-column-count: 2) or (-ms-column-count: 2) or (-webkit-column-count: 2)) {
|
||||
.search-results-group .search-result {
|
||||
display: list-item !important;
|
||||
}
|
||||
|
||||
.search-results-group .search-result:after {
|
||||
content: "";
|
||||
}
|
||||
}
|
||||
|
||||
#wrapper {
|
||||
padding-bottom:0px;
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
/* global importScripts, onmessage: true, postMessage, lunr */
|
||||
|
||||
// Load up the lunr library
|
||||
importScripts('../components/lunr.js-0.4.2/lunr.min.js');
|
||||
importScripts('../components/lunr.js-0.5.12/lunr.min.js');
|
||||
|
||||
// Create the lunr index - the docs should be an array of object, each object containing
|
||||
// the path and search terms for a page
|
||||
|
||||
@@ -24,7 +24,26 @@ angular.module('examples', [])
|
||||
|
||||
|
||||
.factory('openPlunkr', ['formPostData', '$http', '$q', function(formPostData, $http, $q) {
|
||||
return function(exampleFolder, clickEvent) {
|
||||
|
||||
var COPYRIGHT = 'Copyright ' + (new Date()).getFullYear() + ' Google Inc. All Rights Reserved.\n'
|
||||
+ 'Use of this source code is governed by an MIT-style license that\n'
|
||||
+ 'can be found in the LICENSE file at http://angular.io/license';
|
||||
var COPYRIGHT_JS_CSS = '\n\n/*\n' + COPYRIGHT + '\n*/';
|
||||
var COPYRIGHT_HTML = '\n\n<!-- \n' + COPYRIGHT + '\n-->';
|
||||
function getCopyright(filename) {
|
||||
switch (filename.substr(filename.lastIndexOf('.'))) {
|
||||
case '.html':
|
||||
return COPYRIGHT_HTML;
|
||||
case '.js':
|
||||
case '.css':
|
||||
return COPYRIGHT_JS_CSS;
|
||||
case '.md':
|
||||
return COPYRIGHT;
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
return function(exampleFolder, clickEvent) {
|
||||
|
||||
var exampleName = 'AngularJS Example';
|
||||
var newWindow = clickEvent.ctrlKey || clickEvent.metaKey;
|
||||
@@ -67,7 +86,7 @@ angular.module('examples', [])
|
||||
var postData = {};
|
||||
|
||||
angular.forEach(files, function(file) {
|
||||
postData['files[' + file.name + ']'] = file.content;
|
||||
postData['files[' + file.name + ']'] = file.content + getCopyright(file.name);
|
||||
});
|
||||
|
||||
postData['tags[0]'] = "angularjs";
|
||||
|
||||
@@ -11,7 +11,15 @@ angular.module('search', [])
|
||||
var MIN_SEARCH_LENGTH = 2;
|
||||
if(q.length >= MIN_SEARCH_LENGTH) {
|
||||
docsSearch(q).then(function(hits) {
|
||||
var results = {};
|
||||
// Make sure the areas are always in the same order
|
||||
var results = {
|
||||
api: [],
|
||||
guide: [],
|
||||
tutorial: [],
|
||||
error: [],
|
||||
misc: []
|
||||
};
|
||||
|
||||
angular.forEach(hits, function(hit) {
|
||||
var area = hit.area;
|
||||
|
||||
|
||||
@@ -35,7 +35,7 @@ angular.module('tutorials', [])
|
||||
'step': '@docTutorialReset'
|
||||
},
|
||||
template:
|
||||
'<p><a href="" ng-click="show=!show;$event.stopPropagation()">Workspace Reset Instructions ➤</a></p>\n' +
|
||||
'<p><button class="btn" ng-click="show=!show">Workspace Reset Instructions ➤</button></p>\n' +
|
||||
'<div class="alert alert-info" ng-show="show">\n' +
|
||||
' <p>Reset the workspace to step {{step}}.</p>' +
|
||||
' <p><pre>git checkout -f step-{{step}}</pre></p>\n' +
|
||||
@@ -43,7 +43,7 @@ angular.module('tutorials', [])
|
||||
'<a href="http://angular.github.io/angular-phonecat/step-{{step}}/app">Step {{step}} Live Demo</a>.</p>\n' +
|
||||
'</div>\n' +
|
||||
'<p>The most important changes are listed below. You can see the full diff on ' +
|
||||
'<a ng-href="https://github.com/angular/angular-phonecat/compare/step-{{step ? (step - 1): \'0~1\'}}...step-{{step}}">GitHub</a>\n' +
|
||||
'<a ng-href="https://github.com/angular/angular-phonecat/compare/step-{{step ? (step - 1): \'0~1\'}}...step-{{step}}" title="See diff on Github">GitHub</a>\n' +
|
||||
'</p>'
|
||||
};
|
||||
});
|
||||
+1
-1
@@ -2,7 +2,7 @@
|
||||
"name": "AngularJS-docs-app",
|
||||
"dependencies": {
|
||||
"jquery": "2.1.1",
|
||||
"lunr.js": "0.4.3",
|
||||
"lunr.js": "0.5.12",
|
||||
"open-sans-fontface": "1.0.4",
|
||||
"google-code-prettify": "1.0.1",
|
||||
"bootstrap": "3.1.1"
|
||||
|
||||
@@ -10,14 +10,14 @@ var Package = require('dgeni').Package;
|
||||
module.exports = new Package('angularjs', [
|
||||
require('dgeni-packages/ngdoc'),
|
||||
require('dgeni-packages/nunjucks'),
|
||||
require('dgeni-packages/examples')
|
||||
require('dgeni-packages/examples'),
|
||||
require('dgeni-packages/git')
|
||||
])
|
||||
|
||||
|
||||
.factory(require('./services/errorNamespaceMap'))
|
||||
.factory(require('./services/getMinerrInfo'))
|
||||
.factory(require('./services/getVersion'))
|
||||
.factory(require('./services/gitData'))
|
||||
|
||||
.factory(require('./services/deployments/debug'))
|
||||
.factory(require('./services/deployments/default'))
|
||||
@@ -26,7 +26,6 @@ module.exports = new Package('angularjs', [
|
||||
|
||||
.factory(require('./inline-tag-defs/type'))
|
||||
|
||||
|
||||
.processor(require('./processors/error-docs'))
|
||||
.processor(require('./processors/index-page'))
|
||||
.processor(require('./processors/keywords'))
|
||||
@@ -43,7 +42,7 @@ module.exports = new Package('angularjs', [
|
||||
|
||||
readFilesProcessor.basePath = path.resolve(__dirname,'../..');
|
||||
readFilesProcessor.sourceFiles = [
|
||||
{ include: 'src/**/*.js', basePath: 'src' },
|
||||
{ include: 'src/**/*.js', exclude: 'src/angular.bind.js', basePath: 'src' },
|
||||
{ include: 'docs/content/**/*.ngdoc', basePath: 'docs/content' }
|
||||
];
|
||||
|
||||
@@ -171,4 +170,8 @@ module.exports = new Package('angularjs', [
|
||||
jqueryDeployment,
|
||||
productionDeployment
|
||||
];
|
||||
})
|
||||
|
||||
.config(function(generateKeywordsProcessor) {
|
||||
generateKeywordsProcessor.docTypesToIgnore = ['componentGroup'];
|
||||
});
|
||||
|
||||
@@ -16,9 +16,11 @@ module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
|
||||
ignoreWordsFile: undefined,
|
||||
areasToSearch: ['api', 'guide', 'misc', 'error', 'tutorial'],
|
||||
propertiesToIgnore: [],
|
||||
docTypesToIgnore: [],
|
||||
$validate: {
|
||||
ignoreWordsFile: { },
|
||||
areasToSearch: { presence: true },
|
||||
docTypesToIgnore: { },
|
||||
propertiesToIgnore: { }
|
||||
},
|
||||
$runAfter: ['memberDocsProcessor'],
|
||||
@@ -28,6 +30,7 @@ module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
|
||||
// Keywords to ignore
|
||||
var wordsToIgnore = [];
|
||||
var propertiesToIgnore;
|
||||
var docTypesToIgnore;
|
||||
var areasToSearch;
|
||||
|
||||
// Keywords start with "ng:" or one of $, _ or a letter
|
||||
@@ -47,6 +50,8 @@ module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
|
||||
areasToSearch = _.indexBy(this.areasToSearch);
|
||||
propertiesToIgnore = _.indexBy(this.propertiesToIgnore);
|
||||
log.debug('Properties to ignore', propertiesToIgnore);
|
||||
docTypesToIgnore = _.indexBy(this.docTypesToIgnore);
|
||||
log.debug('Doc types to ignore', docTypesToIgnore);
|
||||
|
||||
var ignoreWordsMap = _.indexBy(wordsToIgnore);
|
||||
|
||||
@@ -78,34 +83,36 @@ module.exports = function generateKeywordsProcessor(log, readFilesProcessor) {
|
||||
|
||||
// We are only interested in docs that live in the right area
|
||||
docs = _.filter(docs, function(doc) { return areasToSearch[doc.area]; });
|
||||
docs = _.filter(docs, function(doc) { return !docTypesToIgnore[doc.docType]; });
|
||||
|
||||
_.forEach(docs, function(doc) {
|
||||
|
||||
var words = [];
|
||||
var keywordMap = _.clone(ignoreWordsMap);
|
||||
var members = [];
|
||||
var membersMap = {};
|
||||
|
||||
// Search each top level property of the document for search terms
|
||||
_.forEach(doc, function(value, key) {
|
||||
var words = [];
|
||||
var keywordMap = _.clone(ignoreWordsMap);
|
||||
var members = [];
|
||||
var membersMap = {};
|
||||
|
||||
if ( _.isString(value) && !propertiesToIgnore[key] ) {
|
||||
extractWords(value, words, keywordMap);
|
||||
}
|
||||
// Search each top level property of the document for search terms
|
||||
_.forEach(doc, function(value, key) {
|
||||
|
||||
if ( key === 'methods' || key === 'properties' || key === 'events' ) {
|
||||
_.forEach(value, function(member) {
|
||||
extractWords(member.name, members, membersMap);
|
||||
});
|
||||
}
|
||||
});
|
||||
if ( _.isString(value) && !propertiesToIgnore[key] ) {
|
||||
extractWords(value, words, keywordMap);
|
||||
}
|
||||
|
||||
if ( key === 'methods' || key === 'properties' || key === 'events' ) {
|
||||
_.forEach(value, function(member) {
|
||||
extractWords(member.name, members, membersMap);
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
doc.searchTerms = {
|
||||
titleWords: extractTitleWords(doc.name),
|
||||
keywords: _.sortBy(words).join(' '),
|
||||
members: _.sortBy(members).join(' ')
|
||||
};
|
||||
doc.searchTerms = {
|
||||
titleWords: extractTitleWords(doc.name),
|
||||
keywords: _.sortBy(words).join(' '),
|
||||
members: _.sortBy(members).join(' ')
|
||||
};
|
||||
|
||||
});
|
||||
|
||||
|
||||
@@ -1,16 +0,0 @@
|
||||
"use strict";
|
||||
|
||||
var versionInfo = require('../../../lib/versions/version-info');
|
||||
|
||||
/**
|
||||
* @dgService gitData
|
||||
* @description
|
||||
* Information from the local git repository
|
||||
*/
|
||||
module.exports = function gitData() {
|
||||
return {
|
||||
version: versionInfo.currentVersion,
|
||||
versions: versionInfo.previousVersions,
|
||||
info: versionInfo.gitRepoInfo
|
||||
};
|
||||
};
|
||||
@@ -76,7 +76,7 @@
|
||||
<div class="row">
|
||||
<div class="col-md-9 header-branding">
|
||||
<a class="brand navbar-brand" href="http://angularjs.org">
|
||||
<img width="117" height="30" class="logo" ng-src="img/angularjs-for-header-only.svg">
|
||||
<img width="117" height="30" class="logo" alt="Link to Angular JS Homepage" ng-src="img/angularjs-for-header-only.svg">
|
||||
</a>
|
||||
<ul class="nav navbar-nav">
|
||||
<li class="divider-vertical"></li>
|
||||
@@ -90,7 +90,7 @@
|
||||
<li class="disabled"><a href="http://angularjs.org/">Why AngularJS?</a></li>
|
||||
<li><a href="http://www.youtube.com/user/angularjs">Watch</a></li>
|
||||
<li><a href="tutorial">Tutorial</a></li>
|
||||
<li><a href="http://builtwith.angularjs.org/">Case Studies</a></li>
|
||||
<li><a href="https://www.madewithangular.com/">Case Studies</a></li>
|
||||
<li><a href="https://github.com/angular/angular-seed">Seed App project template</a></li>
|
||||
<li><a href="misc/faq">FAQ</a></li>
|
||||
</ul>
|
||||
@@ -147,13 +147,13 @@
|
||||
<div class="search-results-container" ng-show="hasResults">
|
||||
<div class="container">
|
||||
<div class="search-results-frame">
|
||||
<div ng-repeat="(key, value) in results" class="search-results-group" ng-class="colClassName + ' col-group-' + key">
|
||||
<div ng-repeat="(key, value) in results track by key" class="search-results-group" ng-class="colClassName + ' col-group-' + key" ng-show="value.length > 0">
|
||||
<h4 class="search-results-group-heading">{{ key }}</h4>
|
||||
<div class="search-results">
|
||||
<div ng-repeat="item in value" class="search-result">
|
||||
- <a ng-click="hideResults()" ng-href="{{ item.path }}">{{ item.name }}</a>
|
||||
</div>
|
||||
</div>
|
||||
<ul class="search-results">
|
||||
<!-- Do not insert a line break between li and a. Chrome will insert an actual line-break, which breaks the list item view.
|
||||
TODO: use a html minifier instead -->
|
||||
<li ng-repeat="item in value" class="search-result"><a ng-click="hideResults()" ng-href="{{ item.path }}">{{ item.name }}</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
<a href="" ng-click="hideResults()" class="search-close">
|
||||
@@ -220,10 +220,10 @@
|
||||
<p class="pull-right"><a back-to-top>Back to top</a></p>
|
||||
|
||||
<p>
|
||||
Super-powered by Google ©2010-2015
|
||||
Super-powered by Google ©2010-2016
|
||||
( <a id="version"
|
||||
ng-href="https://github.com/angular/angular.js/blob/master/CHANGELOG.md#{{versionNumber}}"
|
||||
ng-bind-template="v{{version}}">
|
||||
ng-bind-template="v{{version}}" title="Changelog of this version of Angular JS">
|
||||
</a>
|
||||
)
|
||||
</p>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
{# Be aware that we need these extra new lines here or marked will not realise that the <div>
|
||||
{# Be aware that we need these extra new lines here or marked will not realize that the <div>
|
||||
is HTML and wrap each line in a <p> - thus breaking the HTML #}
|
||||
|
||||
<div>
|
||||
@@ -24,5 +24,5 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{# Be aware that we need these extra new lines here or marked will not realise that the <div>
|
||||
{# Be aware that we need these extra new lines here or marked will not realize that the <div>
|
||||
above is HTML and wrap each line in a <p> - thus breaking the HTML #}
|
||||
|
||||
@@ -8,7 +8,7 @@ but the required directive controller is not present on the current DOM element
|
||||
|
||||
To resolve this error ensure that there is no typo in the required controller name and that the required directive controller is present on the current element.
|
||||
|
||||
If the required controller is expected to be on a ancestor element, make sure that you prefix the controller name in the `require` definition with `^`.
|
||||
If the required controller is expected to be on an ancestor element, make sure that you prefix the controller name in the `require` definition with `^`.
|
||||
|
||||
If the required controller is optionally requested, use `?` or `^?` to specify that.
|
||||
|
||||
|
||||
@@ -11,7 +11,7 @@ Supported formats:
|
||||
1. `__name__`
|
||||
2. `__name__ as __identifier__`
|
||||
|
||||
N'either `__name__` or `__identifier__` may contain spaces.
|
||||
Neither `__name__` or `__identifier__` may contain spaces.
|
||||
|
||||
Example of incorrect usage that leads to this error:
|
||||
```html
|
||||
|
||||
@@ -0,0 +1,45 @@
|
||||
@ngdoc error
|
||||
@name $http:legacy
|
||||
@fullName The `success` and `error` methods on the promise returned from `$http` have been disabled.
|
||||
@description
|
||||
|
||||
This error occurs when the legacy promise extensions (`success` and `error`)
|
||||
{@link $httpProvider#useLegacyPromiseExtensions legacy `$http` promise extensions} have been disabled.
|
||||
|
||||
To resolve this error, either turn on the legacy extensions by adding
|
||||
`$httpProvider.useLegacyPromiseExtensions(true);` to your application's configuration; or refactor you
|
||||
use of `$http` to use `.then()` rather than `.success()` and `.error()`.
|
||||
|
||||
For example if you code looked like this:
|
||||
|
||||
```js
|
||||
// Simple GET request example :
|
||||
$http.get('/someUrl').
|
||||
success(function(data, status, headers, config) {
|
||||
// This callback will be called asynchronously
|
||||
// when the response is available
|
||||
}).
|
||||
error(function(data, status, headers, config) {
|
||||
// called asynchronously if an error occurs
|
||||
// or server returns response with an error status.
|
||||
});
|
||||
```
|
||||
|
||||
then you would change it to look like:
|
||||
|
||||
```js
|
||||
// Simple GET request example :
|
||||
$http.get('/someUrl').
|
||||
then(function(response) {
|
||||
// (The response object contains the data, status, headers and config properties)
|
||||
// This callback will be called asynchronously
|
||||
// when the response is available.
|
||||
}, function(response) {
|
||||
// called asynchronously if an error occurs
|
||||
// or server returns response with an error status.
|
||||
});
|
||||
```
|
||||
|
||||
For more information, see the
|
||||
{@link $httpProvider#useLegacyPromiseExtensions `$httpProvider.useLegacyPromiseExtensions`}
|
||||
documentation.
|
||||
@@ -6,6 +6,9 @@
|
||||
This error occurs when a module fails to load due to some exception. The error
|
||||
message above should provide additional context.
|
||||
|
||||
A common reason why the module fails to load is that you've forgotten to
|
||||
include the file with the defined module or that the file couldn't be loaded.
|
||||
|
||||
### Using `ngRoute`
|
||||
|
||||
In AngularJS `1.2.0` and later, `ngRoute` has been moved to its own module.
|
||||
@@ -24,4 +27,4 @@ angular.module('ng').filter('tel', function (){});
|
||||
|
||||
Instead create your own module and add it as a dependency to your application's top-level module.
|
||||
See [#9692](https://github.com/angular/angular.js/issues/9692) and
|
||||
[#7709](https://github.com/angular/angular.js/issues/7709) for more information
|
||||
[#7709](https://github.com/angular/angular.js/issues/7709) for more information
|
||||
|
||||
@@ -81,3 +81,6 @@ angular.module('myModule', [])
|
||||
// a scope object cannot be injected into a service.
|
||||
}]);
|
||||
```
|
||||
|
||||
If you encounter this error only with minified code, consider using `ngStrictDi` (see
|
||||
{@link ng.directive:ngApp ngApp}) to provoke the error with the non-minified source.
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
@ngdoc error
|
||||
@name $location:nobase
|
||||
@fullName $location in HTML5 mode requires a <base> tag to be present!
|
||||
@fullName $location in HTML5 mode requires a `<base>` tag to be present!
|
||||
@description
|
||||
|
||||
If you configure {@link ng.$location `$location`} to use
|
||||
@@ -15,7 +15,7 @@ $locationProvider.html5Mode({
|
||||
});
|
||||
```
|
||||
|
||||
Note that removing the requirement for a <base> tag will have adverse side effects when resolving
|
||||
Note that removing the requirement for a `<base>` tag will have adverse side effects when resolving
|
||||
relative paths with `$location` in IE9.
|
||||
|
||||
The base URL is then used to resolve all relative URLs throughout the application regardless of the
|
||||
|
||||
@@ -14,3 +14,32 @@ perform this check - it's up to the developer to not expose such sensitive and p
|
||||
directly on the scope chain.
|
||||
|
||||
To resolve this error, avoid Window access.
|
||||
|
||||
### Common CoffeeScript Issue
|
||||
|
||||
Be aware that if you are using CoffeeScript, it automatically returns the value of the last statement in a
|
||||
function. So for instance
|
||||
|
||||
```coffeescript
|
||||
scope.foo = ->
|
||||
window.open 'https://example.com'
|
||||
```
|
||||
|
||||
compiles to something like
|
||||
|
||||
```js
|
||||
scope.foo = function() {
|
||||
return window.open('https://example.com');
|
||||
};
|
||||
```
|
||||
|
||||
You can see that this function will return the result of calling `window.open`, which is a `Window`
|
||||
object.
|
||||
|
||||
You can avoid this by explicitly returning something else from the function:
|
||||
|
||||
```coffeescript
|
||||
scope.foo = ->
|
||||
window.open 'https://example.com'
|
||||
return true;
|
||||
```
|
||||
|
||||
@@ -100,7 +100,7 @@ To resolve this type of issue, either fix the api to be always synchronous or as
|
||||
your callback handler to always run asynchronously by using the `$timeout` service.
|
||||
|
||||
```
|
||||
function MyController($scope, thirdPartyComponent) {
|
||||
function MyController($scope, $timeout, thirdPartyComponent) {
|
||||
thirdPartyComponent.getData(function(someData) {
|
||||
$timeout(function() {
|
||||
$scope.someData = someData;
|
||||
@@ -161,7 +161,7 @@ In this second scenario, we are already inside a `$digest` when the ngFocus dire
|
||||
call to `$apply()`, causing this error to be thrown.
|
||||
|
||||
It is possible to workaround this problem by moving the call to set the focus outside of the digest,
|
||||
by using `$timeout(fn, 0, false)`, where the `false` value tells Angular not to wrap this `fn` in a
|
||||
by using `$timeout(fn, 0, false)`, where the `false` value tells Angular not to wrap this `fn` in an
|
||||
`$apply` block:
|
||||
|
||||
```
|
||||
@@ -200,7 +200,7 @@ the top of the call stack.
|
||||
Once you have identified this call you work your way up the stack to see what the problem is.
|
||||
|
||||
* If the second call was made in your application code then you should look at why this code has been
|
||||
called from within a `$apply`/`$digest`. It may be a simple oversight or maybe it fits with the
|
||||
called from within an `$apply`/`$digest`. It may be a simple oversight or maybe it fits with the
|
||||
sync/async scenario described earlier.
|
||||
|
||||
* If the second call was made inside an Angular directive then it is likely that it matches the second
|
||||
|
||||
@@ -1,11 +0,0 @@
|
||||
@ngdoc error
|
||||
@name $sanitize:badparse
|
||||
@fullName Parsing Error while Sanitizing
|
||||
@description
|
||||
|
||||
This error occurs when the HTML string passed to '$sanitize' can't be parsed by the sanitizer.
|
||||
The error contains part of the html string that can't be parsed.
|
||||
|
||||
The parser is more strict than a typical browser parser, so it's possible that some obscure input would produce this error despite the string being recognized as valid HTML by a browser.
|
||||
|
||||
If a valid html code results in this error, please file a bug.
|
||||
@@ -0,0 +1,10 @@
|
||||
@ngdoc error
|
||||
@name $sanitize:noinert
|
||||
@fullName Can't create an inert html document
|
||||
@description
|
||||
|
||||
This error occurs when `$sanitize` sanitizer determines that `document.implementation.createHTMLDocument ` api is not supported by the current browser.
|
||||
|
||||
This api is necessary for safe parsing of HTML strings into DOM trees and without it the sanitizer can't sanitize the input.
|
||||
|
||||
The api is present in all supported browsers including IE 9.0, so the presence of this error usually indicates that Angular's `$sanitize` is being used on an unsupported platform.
|
||||
@@ -0,0 +1,13 @@
|
||||
@ngdoc error
|
||||
@name $sanitize:uinput
|
||||
@fullName Failed to sanitize html because the input is unstable
|
||||
@description
|
||||
|
||||
This error occurs when `$sanitize` sanitizer tries to check the input for possible mXSS payload and the verification
|
||||
errors due to the input mutating indefinitely. This could be a sign that the payload contains code exploiting an mXSS
|
||||
vulnerability in the browser.
|
||||
|
||||
mXSS attack exploit browser bugs that cause some browsers parse a certain html strings into DOM, which once serialized
|
||||
doesn't match the original input. These browser bugs can be exploited by attackers to create payload which looks
|
||||
harmless to sanitizers, but due to mutations caused by the browser are turned into dangerous code once processed after
|
||||
sanitization.
|
||||
@@ -0,0 +1,16 @@
|
||||
@ngdoc error
|
||||
@name linky:notstring
|
||||
@fullName Not a string
|
||||
@description
|
||||
|
||||
This error occurs when {@link ngSanitize.linky linky} is used with a non-empty, non-string value:
|
||||
```html
|
||||
<div ng-bind-html="42 | linky"></div>
|
||||
```
|
||||
|
||||
`linky` is supposed to be used with string values only, and therefore assumes that several methods
|
||||
(such as `.match()`) are available on the passed in value.
|
||||
The value can be initialized asynchronously and therefore null or undefined won't throw this error.
|
||||
|
||||
If you want to pass non-string values to `linky` (e.g. Objects whose `.toString()` should be
|
||||
utilized), you need to manually convert them to strings.
|
||||
@@ -0,0 +1,28 @@
|
||||
@ngdoc error
|
||||
@name ngModel:nopromise
|
||||
@fullName No promise
|
||||
@description
|
||||
|
||||
The return value of an async validator, must always be a promise. If you want to return a
|
||||
non-promise value, you can convert it to a promise using {@link ng.$q#resolve `$q.resolve()`} or
|
||||
{@link ng.$q#reject `$q.reject()`}.
|
||||
|
||||
Example:
|
||||
|
||||
```
|
||||
.directive('asyncValidator', function($q) {
|
||||
return {
|
||||
require: 'ngModel',
|
||||
link: function(scope, elem, attrs, ngModel) {
|
||||
ngModel.$asyncValidators.myAsyncValidation = function(modelValue, viewValue) {
|
||||
if (/* I don't need to hit the backend API */) {
|
||||
return $q.resolve(); // to mark as valid or
|
||||
// return $q.reject(); // to mark as invalid
|
||||
} else {
|
||||
// ...send a request to the backend and return a promise
|
||||
}
|
||||
};
|
||||
}
|
||||
};
|
||||
})
|
||||
```
|
||||
@@ -1,33 +0,0 @@
|
||||
@ngdoc error
|
||||
@name ngOptions:trkslct
|
||||
@fullName Comprehension expression cannot contain both `select as` and `track by` expressions.
|
||||
@description
|
||||
|
||||
NOTE: This error was introduced in 1.3.0-rc.5, and was removed for 1.3.0-rc.6 in order to
|
||||
not break existing apps.
|
||||
|
||||
This error occurs when 'ngOptions' is passed a comprehension expression that contains both a
|
||||
`select as` expression and a `track by` expression. These two expressions are fundamentally
|
||||
incompatible.
|
||||
|
||||
* Example of bad expression: `<select ng-options="item.subItem as item.label for item in values track by item.id" ng-model="selected">`
|
||||
`values: [{id: 1, label: 'aLabel', subItem: {name: 'aSubItem'}}, {id: 2, label: 'bLabel', subItem: {name: 'bSubItem'}}]`,
|
||||
`$scope.selected = {name: 'aSubItem'};`
|
||||
* track by is always applied to `value`, with purpose to preserve the selection,
|
||||
(to `item` in this case)
|
||||
* To calculate whether an item is selected, `ngOptions` does the following:
|
||||
1. apply `track by` to the values in the array:
|
||||
In the example: [1,2]
|
||||
2. apply `track by` to the already selected value in `ngModel`:
|
||||
In the example: this is not possible, as `track by` refers to `item.id`, but the selected
|
||||
value from `ngModel` is `{name: aSubItem}`.
|
||||
|
||||
Here's an example of how to make this example work by using `track by` without `select as`:
|
||||
|
||||
```
|
||||
<select ng-model="selected" ng-options="item.label for item in values track by item.id">
|
||||
```
|
||||
|
||||
Note: This would store the whole `item` as the model to `scope.selected` instead of `item.subItem`.
|
||||
|
||||
For more information on valid expression syntax, see 'ngOptions' in {@link ng.directive:select select} directive docs.
|
||||
@@ -0,0 +1,52 @@
|
||||
@ngdoc error
|
||||
@name orderBy:notarray
|
||||
@fullName Value is not array-like
|
||||
@description
|
||||
|
||||
This error occurs when {@link ng.orderBy orderBy} is not passed an array-like value:
|
||||
```html
|
||||
<div ng-repeat="(key, value) in myObj | orderBy:someProp">
|
||||
{{ key }} : {{ value }}
|
||||
</div>
|
||||
```
|
||||
|
||||
`orderBy` must be used with an array-like value so a subset of items can be returned.
|
||||
The array can be initialized asynchronously and therefore `null` or `undefined` won't throw this error.
|
||||
|
||||
To use `orderBy` to order the properties of an object, you can create your own array based on that object:
|
||||
```js
|
||||
angular.module('aModule', [])
|
||||
.controller('aController', function($scope) {
|
||||
var myObj = {
|
||||
one: {id: 1, name: 'Some thing'},
|
||||
two: {id: 2, name: 'Another thing'},
|
||||
three: {id: 3, name: 'A third thing'}
|
||||
};
|
||||
|
||||
$scope.arrFromMyObj = Object.keys(myObj).map(function(key) {
|
||||
return myObj[key];
|
||||
});
|
||||
});
|
||||
```
|
||||
That can be used as:
|
||||
```html
|
||||
<label>
|
||||
Order by:
|
||||
<select ng-model="orderProp" ng-options="prop for prop in ['id', 'name']"></select>
|
||||
</label>
|
||||
<div ng-repeat="item in arrFromMyObj | orderBy:orderProp">
|
||||
[{{ item.id }}] {{ item.name }}
|
||||
</div>
|
||||
```
|
||||
|
||||
You could as well convert the object to an array using a filter such as
|
||||
[toArrayFilter](https://github.com/petebacondarwin/angular-toArrayFilter):
|
||||
```html
|
||||
<label>
|
||||
Order by:
|
||||
<select ng-model="orderProp" ng-options="prop for prop in ['id', 'name']"></select>
|
||||
</label>
|
||||
<div ng-repeat="item in myObj | toArray:false | orderBy:orderProp">
|
||||
[{{ item.id }}] {{ item.name }}
|
||||
</div>
|
||||
```
|
||||
@@ -301,7 +301,7 @@ it('should show example', inject(
|
||||
### Fallback for legacy browsers
|
||||
|
||||
For browsers that support the HTML5 history API, `$location` uses the HTML5 history API to write
|
||||
path and search. If the history API is not supported by a browser, `$location` supplies a Hasbang
|
||||
path and search. If the history API is not supported by a browser, `$location` supplies a Hashbang
|
||||
URL. This frees you from having to worry about whether the browser viewing your app supports the
|
||||
history API or not; the `$location` service makes this transparent to you.
|
||||
|
||||
@@ -356,15 +356,15 @@ legacy browsers and hashbang links in modern browser:
|
||||
|
||||
### Example
|
||||
|
||||
Here you can see two `$location` instances, both in **Html5 mode**, but on different browsers, so
|
||||
that you can see the differences. These `$location` services are connected to a fake browsers. Each
|
||||
input represents the address bar of the browser.
|
||||
Here you can see two `$location` instances that show the difference between **Html5 mode** and **Html5 Fallback mode**.
|
||||
Note that to simulate different levels of browser support, the `$location` instances are connected to
|
||||
a fakeBrowser service, which you don't have to set up in actual projects.
|
||||
|
||||
Note that when you type hashbang url into first browser (or vice versa) it doesn't rewrite /
|
||||
Note that when you type hashbang url into the first browser (or vice versa) it doesn't rewrite /
|
||||
redirect to regular / hashbang url, as this conversion happens only during parsing the initial URL
|
||||
= on page reload.
|
||||
|
||||
In these examples we use `<base href="/base/index.html" />`
|
||||
In these examples we use `<base href="/base/index.html" />`. The inputs represent the address bar of the browser.
|
||||
|
||||
#### Browser in HTML5 mode
|
||||
<example module="html5-mode" name="location-html5-mode">
|
||||
@@ -389,6 +389,7 @@ In these examples we use `<base href="/base/index.html" />`
|
||||
<file name="app.js">
|
||||
angular.module('html5-mode', ['fake-browser', 'address-bar'])
|
||||
|
||||
// Configure the fakeBrowser. Do not set these values in actual projects.
|
||||
.constant('initUrl', 'http://www.example.com/base/path?a=b#h')
|
||||
.constant('baseHref', '/base/index.html')
|
||||
.value('$sniffer', { history: true })
|
||||
@@ -538,6 +539,7 @@ In these examples we use `<base href="/base/index.html" />`
|
||||
<file name="app.js">
|
||||
angular.module('hashbang-mode', ['fake-browser', 'address-bar'])
|
||||
|
||||
// Configure the fakeBrowser. Do not set these values in actual projects.
|
||||
.constant('initUrl', 'http://www.example.com/base/index.html#!/path?a=b#h')
|
||||
.constant('baseHref', '/base/index.html')
|
||||
.value('$sniffer', { history: false })
|
||||
@@ -693,7 +695,7 @@ A path should always begin with forward slash (`/`); the `$location.path()` sett
|
||||
forward slash if it is missing.
|
||||
|
||||
Note that the `!` prefix in the hashbang mode is not part of `$location.path()`; it is actually
|
||||
hashPrefix.
|
||||
`hashPrefix`.
|
||||
|
||||
## Crawling your app
|
||||
|
||||
@@ -769,8 +771,8 @@ then uses the information it obtains to compose hashbang URLs (such as
|
||||
</tr>
|
||||
|
||||
<tr class="head">
|
||||
<td>Navigation outside the app</td>
|
||||
<td>Use lower level API</td>
|
||||
<th>Navigation outside the app</td>
|
||||
<th>Use lower level API</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
@@ -784,8 +786,8 @@ then uses the information it obtains to compose hashbang URLs (such as
|
||||
</tr>
|
||||
|
||||
<tr class="head">
|
||||
<td>Read access</td>
|
||||
<td>Change to</td>
|
||||
<th>Read access</td>
|
||||
<th>Change to</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
|
||||
@@ -23,9 +23,9 @@ angular.module('myApp', ['ngAria'])...
|
||||
###Using ngAria
|
||||
Most of what ngAria does is only visible "under the hood". To see the module in action, once you've
|
||||
added it as a dependency, you can test a few things:
|
||||
* Using your favorite element inspector, look for ngAria attributes in your own code.
|
||||
* Using your favorite element inspector, look for attributes added by ngAria in your own code.
|
||||
* Test using your keyboard to ensure `tabindex` is used correctly.
|
||||
* Fire up a screen reader such as VoiceOver to listen for ARIA support.
|
||||
* Fire up a screen reader such as VoiceOver or NVDA to check for ARIA support.
|
||||
[Helpful screen reader tips.](http://webaim.org/articles/screenreader_testing/)
|
||||
|
||||
##Supported directives
|
||||
@@ -33,6 +33,9 @@ Currently, ngAria interfaces with the following directives:
|
||||
|
||||
* {@link guide/accessibility#ngmodel ngModel}
|
||||
* {@link guide/accessibility#ngdisabled ngDisabled}
|
||||
* {@link guide/accessibility#ngrequired ngRequired}
|
||||
* {@link guide/accessibility#ngvaluechecked ngChecked}
|
||||
* {@link guide/accessibility#ngvaluechecked ngValue}
|
||||
* {@link guide/accessibility#ngshow ngShow}
|
||||
* {@link guide/accessibility#nghide ngHide}
|
||||
* {@link guide/accessibility#ngclick ngClick}
|
||||
@@ -41,8 +44,8 @@ Currently, ngAria interfaces with the following directives:
|
||||
|
||||
<h2 id="ngmodel">ngModel</h2>
|
||||
|
||||
Most of ngAria's heavy lifting happens in the {@link ngModel ngModel}
|
||||
directive. For elements using ngModel, special attention is paid by ngAria if that element also
|
||||
Much of ngAria's heavy lifting happens in the {@link ng.ngModel ngModel}
|
||||
directive. For elements using ngModel, special attention is paid by ngAria if that element also
|
||||
has a role or type of `checkbox`, `radio`, `range` or `textbox`.
|
||||
|
||||
For those elements using ngModel, ngAria will dynamically bind and update the following ARIA
|
||||
@@ -134,37 +137,75 @@ attributes (if they have not been explicitly specified by the developer):
|
||||
|
||||
ngAria will also add `tabIndex`, ensuring custom elements with these roles will be reachable from
|
||||
the keyboard. It is still up to **you** as a developer to **ensure custom controls will be
|
||||
operable** from the keybard. Think of `ng-click` on a `<div>` or `<md-checkbox>`: you still need
|
||||
to bind `ng-keypress` to make it fully operable from the keyboard. As a rule, any time you create
|
||||
a widget involving user interaction, be sure to test it with your keyboard and at least one mobile
|
||||
and desktop screen reader (preferably more).
|
||||
accessible**. As a rule, any time you create a widget involving user interaction, be sure to test
|
||||
it with your keyboard and at least one mobile and desktop screen reader.
|
||||
|
||||
<h2 id="ngvaluechecked">ngValue and ngChecked</h2>
|
||||
|
||||
To ease the transition between native inputs and custom controls, ngAria now supports
|
||||
{@link ng.ngValue ngValue} and {@link ng.ngChecked ngChecked}.
|
||||
The original directives were created for native inputs only, so ngAria extends
|
||||
support to custom elements by managing `aria-checked` for accessibility.
|
||||
|
||||
###Example
|
||||
|
||||
```html
|
||||
<custom-checkbox ng-checked="val"></custom-checkbox>
|
||||
<custom-radio-button ng-value="val"></custom-radio-button>
|
||||
```
|
||||
|
||||
Becomes:
|
||||
|
||||
```html
|
||||
<custom-checkbox ng-checked="val" aria-checked="true"></custom-checkbox>
|
||||
<custom-radio-button ng-value="val" aria-checked="true"></custom-radio-button>
|
||||
```
|
||||
|
||||
<h2 id="ngdisabled">ngDisabled</h2>
|
||||
|
||||
The `disabled` attribute is only valid for certain elements such as `button`, `input` and
|
||||
`textarea`. To properly disable custom element directives such as `<md-checkbox>` or `<taco-tab>`,
|
||||
using ngAria with [ngDisabled](https://docs.angularjs.org/api/ng/directive/ngDisabled) will also
|
||||
using ngAria with {@link ng.ngDisabled ngDisabled} will also
|
||||
add `aria-disabled`. This tells assistive technologies when a non-native input is disabled, helping
|
||||
custom controls to be more accessible.
|
||||
|
||||
###Example
|
||||
|
||||
```html
|
||||
<md-checkbox ng-disabled="disabled">
|
||||
<md-checkbox ng-disabled="disabled"></md-checkbox>
|
||||
```
|
||||
|
||||
Becomes:
|
||||
|
||||
```html
|
||||
<md-checkbox disabled aria-disabled="true">
|
||||
<md-checkbox disabled aria-disabled="true"></md-checkbox>
|
||||
```
|
||||
|
||||
>You can check whether a control is legitimately disabled for a screen reader by visiting
|
||||
[chrome://accessibility](chrome://accessibility).
|
||||
[chrome://accessibility](chrome://accessibility) and inspecting [the accessibility tree](http://www.paciellogroup.com/blog/2015/01/the-browser-accessibility-tree/).
|
||||
|
||||
<h2 id="ngrequired">ngRequired</h2>
|
||||
|
||||
The boolean `required` attribute is only valid for native form controls such as `input` and
|
||||
`textarea`. To properly indicate custom element directives such as `<md-checkbox>` or `<custom-input>`
|
||||
as required, using ngAria with {@link ng.ngRequired ngRequired} will also add
|
||||
`aria-required`. This tells accessibility APIs when a custom control is required.
|
||||
|
||||
###Example
|
||||
|
||||
```html
|
||||
<md-checkbox ng-required="val"></md-checkbox>
|
||||
```
|
||||
|
||||
Becomes:
|
||||
|
||||
```html
|
||||
<md-checkbox ng-required="val" aria-required="true"></md-checkbox>
|
||||
```
|
||||
|
||||
<h2 id="ngshow">ngShow</h2>
|
||||
|
||||
>The [ngShow](https://docs.angularjs.org/api/ng/directive/ngShow) directive shows or hides the
|
||||
>The {@link ng.ngShow ngShow} directive shows or hides the
|
||||
given HTML element based on the expression provided to the `ngShow` attribute. The element is
|
||||
shown or hidden by removing or adding the `.ng-hide` CSS class onto the element.
|
||||
|
||||
@@ -201,7 +242,7 @@ Becomes:
|
||||
|
||||
<h2 id="nghide">ngHide</h2>
|
||||
|
||||
>The [ngHide](https://docs.angularjs.org/api/ng/directive/ngHide) directive shows or hides the
|
||||
>The {@link ng.ngHide ngHide} directive shows or hides the
|
||||
given HTML element based on the expression provided to the `ngHide` attribute. The element is
|
||||
shown or hidden by removing or adding the `.ng-hide` CSS class onto the element.
|
||||
|
||||
@@ -210,16 +251,25 @@ The default CSS for `ngHide`, the inverse method to `ngShow`, makes ngAria redun
|
||||
`display: none`. See explanation for {@link guide/accessibility#ngshow ngShow} when overriding the default CSS.
|
||||
|
||||
<h2><span id="ngclick">ngClick</span> and <span id="ngdblclick">ngDblclick</span></h2>
|
||||
If `ng-click` or `ng-dblclick` is encountered, ngAria will add `tabindex="0"` if it isn't there
|
||||
already.
|
||||
If `ng-click` or `ng-dblclick` is encountered, ngAria will add `tabindex="0"` to any element not in
|
||||
a node blacklist:
|
||||
|
||||
To fix widespread accessibility problems with `ng-click` on div elements, ngAria will dynamically
|
||||
bind keypress by default as long as the element isn't an anchor, button, input or textarea.
|
||||
You can turn this functionality on or off with the `bindKeypress` configuration option. ngAria
|
||||
will also add the `button` role to communicate to users of assistive technologies.
|
||||
* Button
|
||||
* Anchor
|
||||
* Input
|
||||
* Textarea
|
||||
* Select
|
||||
* Details/Summary
|
||||
|
||||
For `ng-dblclick`, you must still manually add `ng-keypress` and role to non-interactive elements such
|
||||
as `div` or `taco-button` to enable keyboard access.
|
||||
To fix widespread accessibility problems with `ng-click` on `div` elements, ngAria will
|
||||
dynamically bind a keypress event by default as long as the element isn't in the node blacklist.
|
||||
You can turn this functionality on or off with the `bindKeypress` configuration option.
|
||||
|
||||
ngAria will also add the `button` role to communicate to users of assistive technologies. This can
|
||||
be disabled with the `bindRoleForClick` configuration option.
|
||||
|
||||
For `ng-dblclick`, you must still manually add `ng-keypress` and a role to non-interactive elements
|
||||
such as `div` or `taco-button` to enable keyboard access.
|
||||
|
||||
<h3>Example</h3>
|
||||
```html
|
||||
@@ -260,62 +310,18 @@ The attribute magic of ngAria may not work for every scenario. To disable indivi
|
||||
you can use the {@link ngAria.$ariaProvider#config config} method. Just keep in mind this will
|
||||
tell ngAria to ignore the attribute globally.
|
||||
|
||||
<example module="ngAria_ngDisabledExample" deps="angular-aria.js">
|
||||
<example module="ngAria_ngClickExample" deps="angular-aria.js">
|
||||
<file name="index.html">
|
||||
<style>
|
||||
[role=checkbox] {
|
||||
cursor: pointer;
|
||||
display: inline-block;
|
||||
}
|
||||
[role=checkbox] .icon:before {
|
||||
content: '\2610';
|
||||
display: inline-block;
|
||||
font-size: 2em;
|
||||
line-height: 1;
|
||||
vertical-align: middle;
|
||||
speak: none;
|
||||
}
|
||||
[role=checkbox].active .icon:before {
|
||||
content: '\2611';
|
||||
}
|
||||
</style>
|
||||
<form ng-controller="formsController">
|
||||
<div ng-model="someModel" show-attrs>
|
||||
Div with ngModel and aria-invalid disabled
|
||||
<div ng-click="someFunction" show-attrs>
|
||||
<div> with ng-click and bindRoleForClick, tabindex set to false
|
||||
</div>
|
||||
<div role="checkbox" ng-model="checked" ng-class="{active: checked}"
|
||||
aria-label="Custom Checkbox" ng-click="toggleCheckbox()" some-checkbox show-attrs>
|
||||
<span class="icon" aria-hidden="true"></span>
|
||||
Custom Checkbox for comparison
|
||||
</div>
|
||||
</form>
|
||||
<script>
|
||||
angular.module('ngAria_ngDisabledExample', ['ngAria'], function config($ariaProvider) {
|
||||
angular.module('ngAria_ngClickExample', ['ngAria'], function config($ariaProvider) {
|
||||
$ariaProvider.config({
|
||||
ariaInvalid: false,
|
||||
tabindex: true
|
||||
bindRoleForClick: false,
|
||||
tabindex: false
|
||||
});
|
||||
})
|
||||
.controller('formsController', function($scope){
|
||||
$scope.checked = false;
|
||||
$scope.toggleCheckbox = function(){
|
||||
$scope.checked = !$scope.checked;
|
||||
}
|
||||
})
|
||||
.directive('someCheckbox', function(){
|
||||
return {
|
||||
restrict: 'A',
|
||||
link: function($scope, $el, $attrs) {
|
||||
$el.on('keypress', function(event){
|
||||
event.preventDefault();
|
||||
if(event.keyCode === 32 || event.keyCode === 13){
|
||||
$scope.toggleCheckbox();
|
||||
$scope.$apply();
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
})
|
||||
.directive('showAttrs', function() {
|
||||
return function(scope, el, attrs) {
|
||||
var pre = document.createElement('pre');
|
||||
|
||||
@@ -274,6 +274,37 @@ myModule.directive('my-directive', ['$animate', function($animate) {
|
||||
}]);
|
||||
```
|
||||
|
||||
## Preventing flicker before an animation starts
|
||||
|
||||
When nesting elements with structural animations such as `ngIf` into elements that have class-based
|
||||
animations such as `ngClass`, it sometimes happens that before the actual animation starts, there is a brief flicker or flash of content
|
||||
where the animated element is briefly visible.
|
||||
|
||||
To prevent this, you can apply styles to the `ng-[event]-prepare` class, which is added as soon as an animation is initialized,
|
||||
but removed before the actual animation starts (after waiting for a $digest). This class is only added for *structural*
|
||||
animations (`enter`, `move`, and `leave`).
|
||||
|
||||
Here's an example where you might see flickering:
|
||||
|
||||
```html
|
||||
<div ng-class="{red: myProp}">
|
||||
<div ng-class="{blue: myProp}">
|
||||
<div class="message" ng-if="myProp"></div>
|
||||
</div>
|
||||
</div>
|
||||
```
|
||||
|
||||
It is possible that during the `enter` event, the `.message` div will be briefly visible before it starts animating.
|
||||
In that case, you can add styles to the CSS that make sure the element stays hidden before the animation starts:
|
||||
|
||||
```css
|
||||
.message.ng-enter-prepare {
|
||||
opacity: 0;
|
||||
}
|
||||
|
||||
/* Other animation styles ... */
|
||||
```
|
||||
|
||||
## More about animations
|
||||
|
||||
For a full breakdown of each method available on `$animate`, see the {@link ng.$animate API documentation}.
|
||||
|
||||
@@ -0,0 +1,446 @@
|
||||
@ngdoc overview
|
||||
@name Components
|
||||
@sortOrder 305
|
||||
@description
|
||||
|
||||
# Understanding Components
|
||||
|
||||
In Angular, a Component is a special kind of {@link guide/directive directive} that uses a simpler
|
||||
configuration which is suitable for a component-based application structure.
|
||||
|
||||
This makes it easier to write an app in a way that's similar to using Web Components or using Angular
|
||||
2's style of application architecture.
|
||||
|
||||
Advantages of Components:
|
||||
- simpler configuration than plain directives
|
||||
- promote sane defaults and best practices
|
||||
- optimized for component-based architecture
|
||||
- writing component directives will make it easier to upgrade to Angular 2
|
||||
|
||||
When not to use Components:
|
||||
|
||||
- for directives that rely on DOM manipulation, adding event listeners etc, because the compile
|
||||
and link functions are unavailable
|
||||
- when you need advanced directive definition options like priority, terminal, multi-element
|
||||
- when you want a directive that is triggered by an attribute or CSS class, rather than an element
|
||||
|
||||
## Creating and configuring a Component
|
||||
|
||||
Components can be registered using the `.component()` method of an Angular module (returned by {@link module `angular.module()`}). The method takes two arguments:
|
||||
|
||||
* The name of the Component (as string).
|
||||
* The Component config object (note that, unlike the `.directive()` method, this method does **not** take a factory function.
|
||||
|
||||
<example name="heroComponentSimple" module="heroApp">
|
||||
<file name="index.js">
|
||||
angular.module('heroApp', []).controller('mainCtrl', function() {
|
||||
this.hero = {
|
||||
name: 'Spawn'
|
||||
};
|
||||
});
|
||||
</file>
|
||||
<file name="heroDetail.js">
|
||||
|
||||
function HeroDetailController() {
|
||||
|
||||
}
|
||||
|
||||
angular.module('heroApp').component('heroDetail', {
|
||||
templateUrl: 'heroDetail.html',
|
||||
controller: HeroDetailController,
|
||||
bindings: {
|
||||
hero: '='
|
||||
}
|
||||
});
|
||||
</file>
|
||||
<file name="index.html">
|
||||
<!-- components match only elements -->
|
||||
<div ng-controller="mainCtrl as ctrl">
|
||||
<b>Hero</b><br>
|
||||
<hero-detail hero="ctrl.hero"></hero-detail>
|
||||
</div>
|
||||
</file>
|
||||
<file name="heroDetail.html">
|
||||
<span>Name: {{$ctrl.hero.name}}</span>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
It's also possible to add components via {@link $compileProvider#component} in a module's config phase.
|
||||
|
||||
### Comparison between Directive definition and Component definition
|
||||
|
||||
| | Directive | Component |
|
||||
|-------------------|----------------------|-----------------|
|
||||
| bindings | No | Yes (binds to controller) |
|
||||
| bindToController | Yes (default: false) | No (use bindings instead) |
|
||||
| compile function | Yes | No |
|
||||
| controller | Yes | Yes (default `function() {}`) |
|
||||
| controllerAs | Yes (default: false) | Yes (default: `$ctrl`) |
|
||||
| link functions | Yes | No |
|
||||
| multiElement | Yes | No |
|
||||
| priority | Yes | No |
|
||||
| require | Yes | Yes |
|
||||
| restrict | Yes | No (restricted to elements only) |
|
||||
| scope | Yes (default: false) | No (scope is always isolate) |
|
||||
| template | Yes | Yes, injectable |
|
||||
| templateNamespace | Yes | No |
|
||||
| templateUrl | Yes | Yes, injectable |
|
||||
| terminal | Yes | No |
|
||||
| transclude | Yes (default: false) | Yes (default: false) |
|
||||
|
||||
|
||||
## Component-based application architecture
|
||||
|
||||
As already mentioned, the component helper makes it easier to structure your application with
|
||||
a component-based architecture. But what makes a component beyond the options that
|
||||
the component helper has?
|
||||
|
||||
- **Components only control their own View and Data:**
|
||||
Components should never modify any data or DOM that is out of their own scope. Normally, in Angular
|
||||
it is possible to modify data anywhere in the application through scope inheritance and watches. This
|
||||
is practical, but can also lead to problems when it is not clear which part of the application is
|
||||
responsible for modifying the data. That is why component directives use an isolate scope, so a whole
|
||||
class of scope manipulation is not possible.
|
||||
|
||||
- **Components have a well-defined public API - Inputs and Outputs:**
|
||||
However, scope isolation only goes so far, because Angular uses two-way binding. So if you pass
|
||||
an object to a component like this - `bindings: {item: '='}`, and modify one of its properties, the
|
||||
change will be reflected in the parent component. For components however, only the component that owns
|
||||
the data should modify it, to make it easy to reason about what data is changed, and when. For that reason,
|
||||
components should follow a few simple conventions:
|
||||
|
||||
- Inputs are realized with `@` and `=` bindings
|
||||
```js
|
||||
bindings: {
|
||||
hero: `=`,
|
||||
}
|
||||
```
|
||||
- Outputs are realized with `&` bindings, which function as callbacks to component events
|
||||
```js
|
||||
bindings: {
|
||||
onDelete: '&',
|
||||
onUpdate: '&'
|
||||
}
|
||||
```
|
||||
- Instead of manipulating Input Data, the component calls the correct Output Event with the changed data.
|
||||
For a deletion, that means the component doesn't delete the `hero` itself, but sends it back to
|
||||
the owner component via the correct event.
|
||||
```html
|
||||
<button ng-click="$ctrl.onDelete({hero: hero})">Delete</button>
|
||||
```
|
||||
- That way, the parent component can decide what to do with the event (e.g. delete an item or update the properties)
|
||||
```js
|
||||
ctrl.deleteHero(hero) {
|
||||
$http.delete(...).then(function() {
|
||||
var idx = ctrl.list.indexOf(hero);
|
||||
if (idx >= 0) {
|
||||
ctrl.list.splice(idx, 1);
|
||||
}
|
||||
});
|
||||
}
|
||||
```
|
||||
|
||||
- **An application is a tree of components:**
|
||||
Ideally, the whole application should be a tree of components that implement clearly defined inputs
|
||||
and outputs, and minimize two-way data binding. That way, it's easier to predict when data changes and what the state
|
||||
of a component is.
|
||||
|
||||
## Example of a component tree
|
||||
|
||||
The following example expands on the simple component example and incorporates the concepts we introduced
|
||||
above:
|
||||
|
||||
Instead of an ngController, we now have a heroList component that holds the data of
|
||||
different heroes, and creates a heroDetail for each of them.
|
||||
|
||||
The heroDetail component now contains the following new functionality:
|
||||
- a delete button that calls the bound onDelete function of the heroList component
|
||||
- an input to change the hero location, in the form of a reusable editableField component. Instead
|
||||
of manipulating the hero object itself, it sends the changes upwards to the heroDetail, which sends
|
||||
it upwards to the heroList component, which updates it.
|
||||
|
||||
<example name="heroComponentTree" module="heroApp">
|
||||
<file name="index.js">
|
||||
var mode = angular.module('heroApp', []);
|
||||
</file>
|
||||
|
||||
<file name="heroList.js">
|
||||
function HeroListController($scope, $element, $attrs) {
|
||||
var ctrl = this;
|
||||
|
||||
// This would be loaded by $http etc.
|
||||
ctrl.list = [
|
||||
{
|
||||
name: 'Superman',
|
||||
location: ''
|
||||
},
|
||||
{
|
||||
name: 'Batman',
|
||||
location: 'Wayne Manor'
|
||||
}
|
||||
];
|
||||
|
||||
ctrl.updateHero = function(hero, prop, value) {
|
||||
hero[prop] = value;
|
||||
};
|
||||
|
||||
ctrl.deleteHero = function(hero) {
|
||||
var idx = ctrl.list.indexOf(hero);
|
||||
if (idx >= 0) {
|
||||
ctrl.list.splice(idx, 1);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
angular.module('heroApp').component('heroList', {
|
||||
templateUrl: 'heroList.html',
|
||||
controller: HeroListController
|
||||
});
|
||||
|
||||
</file>
|
||||
|
||||
<file name="heroDetail.js">
|
||||
function HeroDetailController($scope, $element, $attrs) {
|
||||
var ctrl = this;
|
||||
|
||||
ctrl.update = function(prop, value) {
|
||||
ctrl.onUpdate({hero: ctrl.hero, prop: prop, value: value});
|
||||
};
|
||||
}
|
||||
|
||||
angular.module('heroApp').component('heroDetail', {
|
||||
templateUrl: 'heroDetail.html',
|
||||
controller: HeroDetailController,
|
||||
bindings: {
|
||||
hero: '=',
|
||||
onDelete: '&',
|
||||
onUpdate: '&'
|
||||
}
|
||||
});
|
||||
</file>
|
||||
|
||||
<file name="editableField.js">
|
||||
|
||||
function EditableFieldController($scope, $element, $attrs) {
|
||||
var ctrl = this;
|
||||
this.editMode = false;
|
||||
|
||||
this.handleModeChange = function() {
|
||||
if (ctrl.editMode) {
|
||||
ctrl.onUpdate({value: ctrl.fieldValue});
|
||||
ctrl.fieldValueCopy = ctrl.fieldValue;
|
||||
}
|
||||
ctrl.editMode = !ctrl.editMode;
|
||||
};
|
||||
|
||||
this.reset = function() {
|
||||
ctrl.fieldValue = ctrl.fieldValueCopy;
|
||||
};
|
||||
|
||||
this.$onInit = function() {
|
||||
// Make a copy of the initial value to be able to reset it later
|
||||
this.fieldValueCopy = this.fieldValue;
|
||||
|
||||
// Set a default fieldType
|
||||
if (!this.fieldType) {
|
||||
this.fieldType = 'text';
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
angular.module('heroApp').component('editableField', {
|
||||
templateUrl: 'editableField.html',
|
||||
controller: EditableFieldController,
|
||||
bindings: {
|
||||
fieldValue: '@',
|
||||
fieldType: '@',
|
||||
onUpdate: '&'
|
||||
}
|
||||
});
|
||||
</file>
|
||||
<file name="index.html">
|
||||
<hero-list></hero-list>
|
||||
</file>
|
||||
<file name="heroList.html">
|
||||
<b>Heroes</b><br>
|
||||
<hero-detail ng-repeat="hero in $ctrl.list" hero="hero" on-delete="$ctrl.deleteHero(hero)" on-update="$ctrl.updateHero(hero, prop, value)"></hero-detail>
|
||||
</file>
|
||||
<file name="heroDetail.html">
|
||||
<hr>
|
||||
<div>
|
||||
Name: {{$ctrl.hero.name}}<br>
|
||||
Location: <editable-field field-value="{{$ctrl.hero.location}}" field-type="text" on-update="$ctrl.update('location', value)"></editable-field><br>
|
||||
<button ng-click="$ctrl.onDelete({hero: $ctrl.hero})">Delete</button>
|
||||
</div>
|
||||
</file>
|
||||
<file name="editableField.html">
|
||||
<span ng-switch="$ctrl.editMode">
|
||||
<input ng-switch-when="true" type="text" ng-model="$ctrl.fieldValue">
|
||||
<span ng-switch-default>{{$ctrl.fieldValue}}</span>
|
||||
</span>
|
||||
<button ng-click="$ctrl.handleModeChange()">{{$ctrl.editMode ? 'Save' : 'Edit'}}</button>
|
||||
<button ng-if="$ctrl.editMode" ng-click="$ctrl.reset()">Reset</button>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
## Components as route templates
|
||||
Components are also useful as route templates (e.g. when using {@link ngRoute ngRoute}). In a component-based
|
||||
application, every view is a component:
|
||||
|
||||
```js
|
||||
var myMod = angular.module('myMod', ['ngRoute']);
|
||||
myMod.component('home', {
|
||||
template: '<h1>Home</h1><p>Hello, {{ $ctrl.user.name }} !</p>',
|
||||
controller: function() {
|
||||
this.user = {name: 'world'};
|
||||
}
|
||||
});
|
||||
myMod.config(function($routeProvider) {
|
||||
$routeProvider.when('/', {
|
||||
template: '<home></home>'
|
||||
});
|
||||
});
|
||||
```
|
||||
<br />
|
||||
When using {@link ngRoute.$routeProvider $routeProvider}, you can often avoid some
|
||||
boilerplate, by assigning the resolved dependencies directly to the route scope:
|
||||
```js
|
||||
var myMod = angular.module('myMod', ['ngRoute']);
|
||||
myMod.component('home', {
|
||||
template: '<h1>Home</h1><p>Hello, {{ $ctrl.user.name }} !</p>',
|
||||
bindings: {user: '='}
|
||||
});
|
||||
myMod.config(function($routeProvider) {
|
||||
$routeProvider.when('/', {
|
||||
template: '<home user="$resolve.user"></home>',
|
||||
resolve: {user: function($http) { return $http.get('...'); }}
|
||||
});
|
||||
});
|
||||
```
|
||||
|
||||
## Intercomponent Communication
|
||||
|
||||
Directives can require the controllers of other directives to enable communication
|
||||
between each other. This can be achieved in a component by providing an
|
||||
object mapping for the `require` property. Here is a tab pane example built
|
||||
from components:
|
||||
|
||||
<example module="docsTabsExample">
|
||||
<file name="script.js">
|
||||
angular.module('docsTabsExample', [])
|
||||
.component('myTabs', {
|
||||
transclude: true,
|
||||
controller: function() {
|
||||
var panes = this.panes = [];
|
||||
this.select = function(pane) {
|
||||
angular.forEach(panes, function(pane) {
|
||||
pane.selected = false;
|
||||
});
|
||||
pane.selected = true;
|
||||
};
|
||||
this.addPane = function(pane) {
|
||||
if (panes.length === 0) {
|
||||
this.select(pane);
|
||||
}
|
||||
panes.push(pane);
|
||||
};
|
||||
},
|
||||
templateUrl: 'my-tabs.html'
|
||||
})
|
||||
.component('myPane', {
|
||||
transclude: true,
|
||||
require: {tabsCtrl: '^myTabs'},
|
||||
bindings: {
|
||||
title: '@'
|
||||
},
|
||||
controller: function() {
|
||||
this.$onInit = function() {
|
||||
this.tabsCtrl.addPane(this);
|
||||
console.log(this);
|
||||
};
|
||||
},
|
||||
templateUrl: 'my-pane.html'
|
||||
});
|
||||
</file>
|
||||
<file name="index.html">
|
||||
<my-tabs>
|
||||
<my-pane title="Hello">
|
||||
<h4>Hello</h4>
|
||||
<p>Lorem ipsum dolor sit amet</p>
|
||||
</my-pane>
|
||||
<my-pane title="World">
|
||||
<h4>World</h4>
|
||||
<em>Mauris elementum elementum enim at suscipit.</em>
|
||||
<p><a href ng-click="i = i + 1">counter: {{i || 0}}</a></p>
|
||||
</my-pane>
|
||||
</my-tabs>
|
||||
</file>
|
||||
<file name="my-tabs.html">
|
||||
<div class="tabbable">
|
||||
<ul class="nav nav-tabs">
|
||||
<li ng-repeat="pane in $ctrl.panes" ng-class="{active:pane.selected}">
|
||||
<a href="" ng-click="$ctrl.select(pane)">{{pane.title}}</a>
|
||||
</li>
|
||||
</ul>
|
||||
<div class="tab-content" ng-transclude></div>
|
||||
</div>
|
||||
</file>
|
||||
<file name="my-pane.html">
|
||||
<div class="tab-pane" ng-show="$ctrl.selected" ng-transclude></div>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
|
||||
# Unit-testing Component Controllers
|
||||
|
||||
The easiest way to unit-test a component controller is by using the {@link ngMock.$componentController $componentController}
|
||||
that is included in {@link ngMock}. The advantage of this method is that you do not have
|
||||
to create any DOM elements. The following example shows how to do this for the `heroDetail` component
|
||||
from above.
|
||||
|
||||
The examples use the [Jasmine](http://jasmine.github.io/) testing framework.
|
||||
|
||||
**Controller Test:**
|
||||
```js
|
||||
describe('component: heroDetail', function() {
|
||||
var component, scope, hero;
|
||||
|
||||
beforeEach(module('simpleComponent'));
|
||||
|
||||
beforeEach(inject(function($rootScope, $componentController) {
|
||||
scope = $rootScope.$new();
|
||||
hero = {name: 'Wolverine'};
|
||||
}));
|
||||
|
||||
it('should set the default values of the hero', function() {
|
||||
// It's necessary to always pass the scope in the locals, so that the controller instance can be bound to it
|
||||
component = $componentController('heroDetail', {$scope: scope});
|
||||
|
||||
expect(component.hero).toEqual({
|
||||
name: undefined,
|
||||
location: 'unknown'
|
||||
});
|
||||
});
|
||||
|
||||
it('should assign the name bindings to the hero object', function() {
|
||||
// Here we are passing actual bindings to the component
|
||||
|
||||
component = $componentController('heroDetail',
|
||||
{$scope: scope},
|
||||
{hero: hero}
|
||||
);
|
||||
expect(component.hero.name).toBe('Wolverine');
|
||||
});
|
||||
|
||||
it('should call the onDelete binding when a hero is deleted', function() {
|
||||
component = $componentController('heroDetail',
|
||||
{$scope: scope},
|
||||
{hero: hero, onDelete: jasmine.createSpy('deleteSpy')}
|
||||
);
|
||||
|
||||
component.onDelete({hero: component.hero});
|
||||
expect(spy('deleteSpy')).toHaveBeenCalledWith(component.hero);
|
||||
});
|
||||
|
||||
});
|
||||
```
|
||||
@@ -8,22 +8,22 @@
|
||||
This section briefly touches on all of the important parts of AngularJS using a simple example.
|
||||
For a more in-depth explanation, see the {@link tutorial/ tutorial}.
|
||||
|
||||
| Concept | Description |
|
||||
|------------------|------------------------------------------|
|
||||
|{@link concepts#template Template} | HTML with additional markup |
|
||||
|{@link concepts#directive Directives} | extend HTML with custom attributes and elements |
|
||||
|{@link concepts#model Model} | the data shown to the user in the view and with which the user interacts |
|
||||
|{@link concepts#scope Scope} | context where the model is stored so that controllers, directives and expressions can access it |
|
||||
|{@link concepts#expression Expressions} | access variables and functions from the scope |
|
||||
|{@link concepts#compiler Compiler} | parses the template and instantiates directives and expressions |
|
||||
|{@link concepts#filter Filter} | formats the value of an expression for display to the user |
|
||||
|{@link concepts#view View} | what the user sees (the DOM) |
|
||||
|{@link concepts#databinding Data Binding} | sync data between the model and the view |
|
||||
|{@link concepts#controller Controller} | the business logic behind views |
|
||||
|{@link concepts#di Dependency Injection} | Creates and wires objects and functions |
|
||||
|{@link concepts#injector Injector} | dependency injection container |
|
||||
|{@link concepts#module Module} | a container for the different parts of an app including controllers, services, filters, directives which configures the Injector |
|
||||
|{@link concepts#service Service} | reusable business logic independent of views |
|
||||
| Concept | Description |
|
||||
|--------------------------------------------|--------------------------------------------------------------------------|
|
||||
|{@link concepts#template Template} | HTML with additional markup |
|
||||
|{@link concepts#directive Directives} | extend HTML with custom attributes and elements |
|
||||
|{@link concepts#model Model} | the data shown to the user in the view and with which the user interacts |
|
||||
|{@link concepts#scope Scope} | context where the model is stored so that controllers, directives and expressions can access it |
|
||||
|{@link concepts#expression Expressions} | access variables and functions from the scope |
|
||||
|{@link concepts#compiler Compiler} | parses the template and instantiates directives and expressions |
|
||||
|{@link concepts#filter Filter} | formats the value of an expression for display to the user |
|
||||
|{@link concepts#view View} | what the user sees (the DOM) |
|
||||
|{@link concepts#databinding Data Binding} | sync data between the model and the view |
|
||||
|{@link concepts#controller Controller} | the business logic behind views |
|
||||
|{@link concepts#di Dependency Injection} | Creates and wires objects and functions |
|
||||
|{@link concepts#injector Injector} | dependency injection container |
|
||||
|{@link concepts#module Module} | a container for the different parts of an app including controllers, services, filters, directives which configures the Injector |
|
||||
|{@link concepts#service Service} | reusable business logic independent of views |
|
||||
|
||||
|
||||
## A first example: Data binding
|
||||
@@ -57,7 +57,7 @@ Try out the Live Preview above, and then let's walk through the example and desc
|
||||
This looks like normal HTML, with some new markup. In Angular, a file like this is called a
|
||||
<a name="template">{@link templates template}</a>. When Angular starts your application, it parses and
|
||||
processes this new markup from the template using the <a name="compiler">{@link compiler compiler}</a>.
|
||||
The loaded, transformed and rendered DOM is then called the <a name="view">view</a>.
|
||||
The loaded, transformed and rendered DOM is then called the <a name="view"></a>*view*.
|
||||
|
||||
The first kind of new markup are the <a name="directive">{@link directive directives}</a>.
|
||||
They apply special behavior to attributes or elements in the HTML. In the example above we use the
|
||||
@@ -76,10 +76,10 @@ stores/updates the value of the input field into/from a variable.
|
||||
The second kind of new markup are the double curly braces `{{ expression | filter }}`:
|
||||
When the compiler encounters this markup, it will replace it with the evaluated value of the markup.
|
||||
An <a name="expression">{@link expression expression}</a> in a template is a JavaScript-like code snippet that allows
|
||||
to read and write variables. Note that those variables are not global variables.
|
||||
Angular to read and write variables. Note that those variables are not global variables.
|
||||
Just like variables in a JavaScript function live in a scope,
|
||||
Angular provides a <a name="scope">{@link scope scope}</a> for the variables accessible to expressions.
|
||||
The values that are stored in variables on the scope are referred to as the <a name="model">model</a>
|
||||
The values that are stored in variables on the scope are referred to as the <a name="model"></a>*model*
|
||||
in the rest of the documentation.
|
||||
Applied to the example above, the markup directs Angular to "take the data we got from the input widgets
|
||||
and multiply them together".
|
||||
@@ -334,9 +334,9 @@ The following example shows how this is done with Angular:
|
||||
var refresh = function() {
|
||||
var url = YAHOO_FINANCE_URL_PATTERN.
|
||||
replace('PAIRS', 'USD' + currencies.join('","USD'));
|
||||
return $http.jsonp(url).success(function(data) {
|
||||
return $http.jsonp(url).then(function(response) {
|
||||
var newUsdToForeignRates = {};
|
||||
angular.forEach(data.query.results.rate, function(rate) {
|
||||
angular.forEach(response.data.query.results.rate, function(rate) {
|
||||
var currency = rate.id.substring(3,6);
|
||||
newUsdToForeignRates[currency] = window.parseFloat(rate.Rate);
|
||||
});
|
||||
@@ -348,8 +348,7 @@ The following example shows how this is done with Angular:
|
||||
|
||||
return {
|
||||
currencies: currencies,
|
||||
convert: convert,
|
||||
refresh: refresh
|
||||
convert: convert
|
||||
};
|
||||
}]);
|
||||
</file>
|
||||
|
||||
@@ -5,13 +5,16 @@
|
||||
|
||||
# Understanding Controllers
|
||||
|
||||
In Angular, a Controller is a JavaScript **constructor function** that is used to augment the
|
||||
In Angular, a Controller is defined by a JavaScript **constructor function** that is used to augment the
|
||||
{@link scope Angular Scope}.
|
||||
|
||||
When a Controller is attached to the DOM via the {@link ng.directive:ngController ng-controller}
|
||||
directive, Angular will instantiate a new Controller object, using the specified Controller's
|
||||
**constructor function**. A new **child scope** will be available as an injectable parameter to the
|
||||
Controller's constructor function as `$scope`.
|
||||
**constructor function**. A new **child scope** will be created and made available as an injectable
|
||||
parameter to the Controller's constructor function as `$scope`.
|
||||
|
||||
If the controller has been attached using the `controller as` syntax then the controller instance will
|
||||
be assigned to a property on the new scope.
|
||||
|
||||
Use controllers to:
|
||||
|
||||
@@ -106,7 +109,7 @@ needed for a single view.
|
||||
|
||||
The most common way to keep Controllers slim is by encapsulating work that doesn't belong to
|
||||
controllers into services and then using these services in Controllers via dependency injection.
|
||||
This is discussed in the {@link di Dependency Injection} {@link services
|
||||
This is discussed in the {@link di Dependency Injection} and {@link services
|
||||
Services} sections of this guide.
|
||||
|
||||
|
||||
@@ -162,7 +165,7 @@ scope is augmented (managed) by the `SpicyController` Controller.
|
||||
starts with capital letter and ends with "Controller".
|
||||
- Assigning a property to `$scope` creates or updates the model.
|
||||
- Controller methods can be created through direct assignment to scope (see the `chiliSpicy` method)
|
||||
- The Controller methods and properties are available in the template (for the `<div>` element and
|
||||
- The Controller methods and properties are available in the template (for both the `<div>` element and
|
||||
its children).
|
||||
|
||||
## Spicy Arguments Example
|
||||
@@ -302,7 +305,7 @@ describe('myController function', function() {
|
||||
```
|
||||
|
||||
|
||||
If you need to test a nested Controller you need to create the same scope hierarchy
|
||||
If you need to test a nested Controller you must create the same scope hierarchy
|
||||
in your test that exists in the DOM:
|
||||
|
||||
```js
|
||||
|
||||
@@ -163,8 +163,8 @@ someModule.controller('MyController', function($scope, greeter) {
|
||||
});
|
||||
```
|
||||
|
||||
Given a function the injector can infer the names of the services to inject by examining the
|
||||
function declaration and extracting the parameter names. In the above example `$scope`, and
|
||||
Given a function, the injector can infer the names of the services to inject by examining the
|
||||
function declaration and extracting the parameter names. In the above example, `$scope` and
|
||||
`greeter` are two services which need to be injected into the function.
|
||||
|
||||
One advantage of this approach is that there's no array of names to keep in sync with the
|
||||
@@ -293,7 +293,7 @@ Create a new injector that can provide components defined in our `myModule` modu
|
||||
`greeter` service from the injector. (This is usually done automatically by angular bootstrap).
|
||||
|
||||
```js
|
||||
var injector = angular.injector(['myModule', 'ng']);
|
||||
var injector = angular.injector(['ng', 'myModule']);
|
||||
var greeter = injector.get('greeter');
|
||||
```
|
||||
|
||||
|
||||
@@ -19,8 +19,9 @@ how to implement them.
|
||||
## What are Directives?
|
||||
|
||||
At a high level, directives are markers on a DOM element (such as an attribute, element
|
||||
name, comment or CSS class) that tell AngularJS's **HTML compiler** ({@link ng.$compile `$compile`}) to
|
||||
attach a specified behavior to that DOM element or even transform the DOM element and its children.
|
||||
name, comment or CSS class) that tell AngularJS's **HTML compiler** ({@link ng.$compile `$compile`})
|
||||
to attach a specified behavior to that DOM element (e.g. via event listeners), or even to transform
|
||||
the DOM element and its children.
|
||||
|
||||
Angular comes with a set of these directives built-in, like `ngBind`, `ngModel`, and `ngClass`.
|
||||
Much like you create controllers and services, you can create your own directives for Angular to use.
|
||||
@@ -30,7 +31,7 @@ When Angular {@link guide/bootstrap bootstraps} your application, the
|
||||
<div class="alert alert-info">
|
||||
**What does it mean to "compile" an HTML template?**
|
||||
|
||||
For AngularJS, "compilation" means attaching event listeners to the HTML to make it interactive.
|
||||
For AngularJS, "compilation" means attaching directives to the HTML to make it interactive.
|
||||
The reason we use the term "compile" is that the recursive process of attaching directives
|
||||
mirrors the process of compiling source code in
|
||||
[compiled programming languages](http://en.wikipedia.org/wiki/Compiled_languages).
|
||||
@@ -42,16 +43,25 @@ mirrors the process of compiling source code in
|
||||
Before we can write a directive, we need to know how Angular's {@link guide/compiler HTML compiler}
|
||||
determines when to use a given directive.
|
||||
|
||||
In the following example, we say that the `<input>` element **matches** the `ngModel` directive.
|
||||
Similar to the terminology used when an [element **matches** a selector](https://developer.mozilla.org/en-US/docs/Web/API/Element.matches), we say an element **matches** a
|
||||
directive when the directive is part of its declaration.
|
||||
|
||||
In the following example, we say that the `<input>` element **matches** the `ngModel` directive
|
||||
|
||||
```html
|
||||
<input ng-model="foo">
|
||||
```
|
||||
|
||||
The following also **matches** `ngModel`:
|
||||
The following `<input>` element also **matches** `ngModel`:
|
||||
|
||||
```html
|
||||
<input data-ng:model="foo">
|
||||
<input data-ng-model="foo">
|
||||
```
|
||||
|
||||
And the following <person> element **matches** the `person` directive:
|
||||
|
||||
```html
|
||||
<person>{{name}}</person>
|
||||
```
|
||||
|
||||
### Normalization
|
||||
@@ -89,8 +99,13 @@ For example, the following forms are all equivalent and match the {@link ngBind}
|
||||
</file>
|
||||
<file name="protractor.js" type="protractor">
|
||||
it('should show off bindings', function() {
|
||||
expect(element(by.css('div[ng-controller="Controller"] span[ng-bind]')).getText())
|
||||
.toBe('Max Karl Ernst Ludwig Planck (April 23, 1858 – October 4, 1947)');
|
||||
var containerElm = element(by.css('div[ng-controller="Controller"]'));
|
||||
var nameBindings = containerElm.all(by.binding('name'));
|
||||
|
||||
expect(nameBindings.count()).toBe(5);
|
||||
nameBindings.each(function(elem) {
|
||||
expect(elem.getText()).toEqual('Max Karl Ernst Ludwig Planck (April 23, 1858 – October 4, 1947)');
|
||||
});
|
||||
});
|
||||
</file>
|
||||
</example>
|
||||
@@ -131,63 +146,6 @@ directives when possible.
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
### Text and attribute bindings
|
||||
|
||||
During the compilation process the {@link ng.$compile compiler} matches text and attributes
|
||||
using the {@link ng.$interpolate $interpolate} service to see if they contain embedded
|
||||
expressions. These expressions are registered as {@link ng.$rootScope.Scope#$watch watches}
|
||||
and will update as part of normal {@link ng.$rootScope.Scope#$digest digest} cycle. An
|
||||
example of interpolation is shown below:
|
||||
|
||||
```html
|
||||
<a ng-href="img/{{username}}.jpg">Hello {{username}}!</a>
|
||||
```
|
||||
|
||||
|
||||
### `ngAttr` attribute bindings
|
||||
|
||||
Web browsers are sometimes picky about what values they consider valid for attributes.
|
||||
|
||||
For example, considering this template:
|
||||
|
||||
```html
|
||||
<svg>
|
||||
<circle cx="{{cx}}"></circle>
|
||||
</svg>
|
||||
```
|
||||
|
||||
We would expect Angular to be able to bind to this, but when we check the console we see
|
||||
something like `Error: Invalid value for attribute cx="{{cx}}"`. Because of the SVG DOM API's
|
||||
restrictions, you cannot simply write `cx="{{cx}}"`.
|
||||
|
||||
With `ng-attr-cx` you can work around this problem.
|
||||
|
||||
If an attribute with a binding is prefixed with the `ngAttr` prefix (denormalized as `ng-attr-`)
|
||||
then during the binding it will be applied to the corresponding unprefixed attribute. This allows
|
||||
you to bind to attributes that would otherwise be eagerly processed by browsers
|
||||
(e.g. an SVG element's `circle[cx]` attributes). When using `ngAttr`, the `allOrNothing` flag of
|
||||
{@link ng.$interpolate $interpolate} is used, so if any expression in the interpolated string
|
||||
results in `undefined`, the attribute is removed and not added to the element.
|
||||
|
||||
For example, we could fix the example above by instead writing:
|
||||
|
||||
```html
|
||||
<svg>
|
||||
<circle ng-attr-cx="{{cx}}"></circle>
|
||||
</svg>
|
||||
```
|
||||
|
||||
If one wants to modify a camelcased attribute (SVG elements have valid camelcased attributes), such as `viewBox` on the `svg` element, one can use underscores to denote that the attribute to bind to is naturally camelcased.
|
||||
|
||||
For example, to bind to `viewBox`, we can write:
|
||||
|
||||
```html
|
||||
<svg ng-attr-view_box="{{viewBox}}">
|
||||
</svg>
|
||||
```
|
||||
|
||||
|
||||
## Creating Directives
|
||||
|
||||
First let's talk about the {@link ng.$compileProvider#directive API for registering directives}. Much like
|
||||
@@ -345,6 +303,7 @@ The `restrict` option is typically set to:
|
||||
* `'A'` - only matches attribute name
|
||||
* `'E'` - only matches element name
|
||||
* `'C'` - only matches class name
|
||||
* `'M'` - only matches comment
|
||||
|
||||
These restrictions can all be combined as needed:
|
||||
|
||||
@@ -448,7 +407,7 @@ This is clearly not a great solution.
|
||||
|
||||
What we want to be able to do is separate the scope inside a directive from the scope
|
||||
outside, and then map the outer scope to a directive's inner scope. We can do this by creating what
|
||||
we call an **isolate scope**. To do this, we can use a directive's `scope` option:
|
||||
we call an **isolate scope**. To do this, we can use a {@link $compile#-scope- directive's `scope`} option:
|
||||
|
||||
<example module="docsIsolateScopeDirective">
|
||||
<file name="script.js">
|
||||
@@ -577,14 +536,24 @@ want to reuse throughout your app.
|
||||
In this example we will build a directive that displays the current time.
|
||||
Once a second, it updates the DOM to reflect the current time.
|
||||
|
||||
Directives that want to modify the DOM typically use the `link` option.
|
||||
`link` takes a function with the following signature, `function link(scope, element, attrs) { ... }`
|
||||
where:
|
||||
Directives that want to modify the DOM typically use the `link` option to register DOM listeners
|
||||
as well as update the DOM. It is executed after the template has been cloned and is where
|
||||
directive logic will be put.
|
||||
|
||||
`link` takes a function with the following signature,
|
||||
`function link(scope, element, attrs, controller, transcludeFn) { ... }`, where:
|
||||
|
||||
* `scope` is an Angular scope object.
|
||||
* `element` is the jqLite-wrapped element that this directive matches.
|
||||
* `attrs` is a hash object with key-value pairs of normalized attribute names and their
|
||||
corresponding attribute values.
|
||||
* `controller` is the directive's required controller instance(s) or its own controller (if any).
|
||||
The exact value depends on the directive's require property.
|
||||
* `transcludeFn` is a transclude linking function pre-bound to the correct transclusion scope.
|
||||
|
||||
<div class="alert alert-info">
|
||||
For more details on the `link` option refer to the {@link ng.$compile#-link- `$compile` API} page.
|
||||
</div>
|
||||
|
||||
In our `link` function, we want to update the displayed time once a second, or whenever a user
|
||||
changes the time formatting string that our directive binds to. We will use the `$interval` service
|
||||
@@ -678,6 +647,7 @@ To do this, we need to use the `transclude` option.
|
||||
return {
|
||||
restrict: 'E',
|
||||
transclude: true,
|
||||
scope: {},
|
||||
templateUrl: 'my-dialog.html'
|
||||
};
|
||||
});
|
||||
@@ -688,8 +658,7 @@ To do this, we need to use the `transclude` option.
|
||||
</div>
|
||||
</file>
|
||||
<file name="my-dialog.html">
|
||||
<div class="alert" ng-transclude>
|
||||
</div>
|
||||
<div class="alert" ng-transclude></div>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
@@ -711,7 +680,7 @@ that redefines `name` as `Jeff`. What do you think the `{{name}}` binding will r
|
||||
transclude: true,
|
||||
scope: {},
|
||||
templateUrl: 'my-dialog.html',
|
||||
link: function (scope, element) {
|
||||
link: function (scope) {
|
||||
scope.name = 'Jeff';
|
||||
}
|
||||
};
|
||||
@@ -723,8 +692,7 @@ that redefines `name` as `Jeff`. What do you think the `{{name}}` binding will r
|
||||
</div>
|
||||
</file>
|
||||
<file name="my-dialog.html">
|
||||
<div class="alert" ng-transclude>
|
||||
</div>
|
||||
<div class="alert" ng-transclude></div>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
@@ -735,7 +703,7 @@ The `transclude` option changes the way scopes are nested. It makes it so that t
|
||||
transcluded directive have whatever scope is outside the directive, rather than whatever scope is on
|
||||
the inside. In doing so, it gives the contents access to the outside scope.
|
||||
|
||||
Note that if the directive did not create its own scope, then `scope` in `scope.name = 'Jeff';` would
|
||||
Note that if the directive did not create its own scope, then `scope` in `scope.name = 'Jeff'` would
|
||||
reference the outside scope and we would see `Jeff` in the output.
|
||||
|
||||
This behavior makes sense for a directive that wraps some content, because otherwise you'd have to
|
||||
@@ -808,9 +776,9 @@ function.
|
||||
|
||||
Often it's desirable to pass data from the isolate scope via an expression to the
|
||||
parent scope, this can be done by passing a map of local variable names and values into the expression
|
||||
wrapper fn. For example, the hideDialog function takes a message to display when the dialog is hidden.
|
||||
This is specified in the directive by calling `close({message: 'closing for now'})`. Then the local
|
||||
variable `message` will be available within the `on-close` expression.
|
||||
wrapper function. For example, the `hideDialog` function takes a message to display when the dialog
|
||||
is hidden. This is specified in the directive by calling `close({message: 'closing for now'})`.
|
||||
Then the local variable `message` will be available within the `on-close` expression.
|
||||
|
||||
<div class="alert alert-success">
|
||||
**Best Practice:** use `&attr` in the `scope` option when you want your directive
|
||||
@@ -869,7 +837,7 @@ element?
|
||||
}]);
|
||||
</file>
|
||||
<file name="index.html">
|
||||
<span my-draggable>Drag ME</span>
|
||||
<span my-draggable>Drag Me</span>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
@@ -892,7 +860,7 @@ to which tab is active.
|
||||
restrict: 'E',
|
||||
transclude: true,
|
||||
scope: {},
|
||||
controller: function($scope) {
|
||||
controller: ['$scope', function($scope) {
|
||||
var panes = $scope.panes = [];
|
||||
|
||||
$scope.select = function(pane) {
|
||||
@@ -908,13 +876,13 @@ to which tab is active.
|
||||
}
|
||||
panes.push(pane);
|
||||
};
|
||||
},
|
||||
}],
|
||||
templateUrl: 'my-tabs.html'
|
||||
};
|
||||
})
|
||||
.directive('myPane', function() {
|
||||
return {
|
||||
require: '^myTabs',
|
||||
require: '^^myTabs',
|
||||
restrict: 'E',
|
||||
transclude: true,
|
||||
scope: {
|
||||
@@ -930,11 +898,9 @@ to which tab is active.
|
||||
<file name="index.html">
|
||||
<my-tabs>
|
||||
<my-pane title="Hello">
|
||||
<h4>Hello</h4>
|
||||
<p>Lorem ipsum dolor sit amet</p>
|
||||
</my-pane>
|
||||
<my-pane title="World">
|
||||
<h4>World</h4>
|
||||
<em>Mauris elementum elementum enim at suscipit.</em>
|
||||
<p><a href ng-click="i = i + 1">counter: {{i || 0}}</a></p>
|
||||
</my-pane>
|
||||
@@ -951,22 +917,25 @@ to which tab is active.
|
||||
</div>
|
||||
</file>
|
||||
<file name="my-pane.html">
|
||||
<div class="tab-pane" ng-show="selected" ng-transclude>
|
||||
<div class="tab-pane" ng-show="selected">
|
||||
<h4>{{title}}</h4>
|
||||
<div ng-transclude></div>
|
||||
</div>
|
||||
</file>
|
||||
</example>
|
||||
|
||||
The `myPane` directive has a `require` option with value `^myTabs`. When a directive uses this
|
||||
option, `$compile` will throw an error unless the specified controller is found. The `^` prefix
|
||||
means that this directive searches for the controller on its parents (without the `^` prefix, the
|
||||
directive would look for the controller on just its own element).
|
||||
The `myPane` directive has a `require` option with value `^^myTabs`. When a directive uses this
|
||||
option, `$compile` will throw an error unless the specified controller is found. The `^^` prefix
|
||||
means that this directive searches for the controller on its parents. (A `^` prefix would make the
|
||||
directive look for the controller on its own element or its parents; without any prefix, the
|
||||
directive would look on its own element only.)
|
||||
|
||||
So where does this `myTabs` controller come from? Directives can specify controllers using
|
||||
the unsurprisingly named `controller` option. As you can see, the `myTabs` directive uses this
|
||||
option. Just like `ngController`, this option attaches a controller to the template of the directive.
|
||||
|
||||
If it is necessary to reference the controller or any functions bound to the controller's scope in
|
||||
the template, you can use the option `controllerAs` to specify the name of the controller as an alias.
|
||||
If it is necessary to reference the controller or any functions bound to the controller from the
|
||||
template, you can use the option `controllerAs` to specify the name of the controller as an alias.
|
||||
The directive needs to define a scope for this configuration to be used. This is particularly useful
|
||||
in the case when the directive is used as a component.
|
||||
|
||||
@@ -981,7 +950,7 @@ The corresponding parameter being sent to the `link` function will also be an ar
|
||||
angular.module('docsTabsExample', [])
|
||||
.directive('myPane', function() {
|
||||
return {
|
||||
require: ['^myTabs', '^ngModel'],
|
||||
require: ['^^myTabs', 'ngModel'],
|
||||
restrict: 'E',
|
||||
transclude: true,
|
||||
scope: {
|
||||
@@ -1017,4 +986,3 @@ available in the {@link guide/compiler compiler guide}.
|
||||
|
||||
The {@link ng.$compile `$compile` API} page has a comprehensive list of directive options for
|
||||
reference.
|
||||
|
||||
|
||||
@@ -5,8 +5,9 @@
|
||||
|
||||
# Angular Expressions
|
||||
|
||||
Angular expressions are JavaScript-like code snippets that are usually placed in bindings such as
|
||||
`{{ expression }}`.
|
||||
Angular expressions are JavaScript-like code snippets that are mainly placed in
|
||||
interpolation bindings such as `<span title="{{ attrBinding }}">{{ textBinding }}</span>`,
|
||||
but also used directly in directive attributes such as `ng-click="functionExpression()"`.
|
||||
|
||||
For example, these are valid expressions in Angular:
|
||||
|
||||
@@ -28,14 +29,16 @@ Angular expressions are like JavaScript expressions with the following differenc
|
||||
|
||||
* **No Control Flow Statements:** You cannot use the following in an Angular expression:
|
||||
conditionals, loops, or exceptions.
|
||||
|
||||
|
||||
* **No Function Declarations:** You cannot declare functions in an Angular expression,
|
||||
even inside `ng-init` directive.
|
||||
|
||||
* **No RegExp Creation With Literal Notation:** You cannot create regular expressions
|
||||
|
||||
* **No RegExp Creation With Literal Notation:** You cannot create regular expressions
|
||||
in an Angular expression.
|
||||
|
||||
* **No Comma And Void Operators:** You cannot use `,` or `void` in an Angular expression.
|
||||
|
||||
* **No Object Creation With New Operator:** You cannot use `new` operator in an Angular expression.
|
||||
|
||||
* **No Comma And Void Operators:** You cannot use `,` or `void` operators in an Angular expression.
|
||||
|
||||
* **Filters:** You can use {@link guide/filter filters} within expressions to format data before
|
||||
displaying it.
|
||||
@@ -70,7 +73,7 @@ You can try evaluating different expressions here:
|
||||
<ul>
|
||||
<li ng-repeat="expr in exprs track by $index">
|
||||
[ <a href="" ng-click="removeExp($index)">X</a> ]
|
||||
<tt>{{expr}}</tt> => <span ng-bind="$parent.$eval(expr)"></span>
|
||||
<code>{{expr}}</code> => <span ng-bind="$parent.$eval(expr)"></span>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
@@ -113,6 +116,9 @@ This restriction is intentional. It prevents accidental access to the global sta
|
||||
Instead use services like `$window` and `$location` in functions called from expressions. Such services
|
||||
provide mockable access to globals.
|
||||
|
||||
It is possible to access the context object using the identifier `this` and the locals object using the
|
||||
identifier `$locals`.
|
||||
|
||||
<example module="expressionExample">
|
||||
<file name="index.html">
|
||||
<div class="example2" ng-controller="ExampleController">
|
||||
@@ -141,6 +147,9 @@ provide mockable access to globals.
|
||||
}
|
||||
element(by.css('[ng-click="greet()"]')).click();
|
||||
|
||||
// We need to give the browser time to display the alert
|
||||
browser.wait(protractor.ExpectedConditions.alertIsPresent(), 1000);
|
||||
|
||||
var alertDialog = browser.switchTo().alert();
|
||||
|
||||
expect(alertDialog.getText()).toEqual('Hello World');
|
||||
@@ -175,7 +184,7 @@ expression, delegate to a JavaScript method instead.
|
||||
## No function declarations or RegExp creation with literal notation
|
||||
|
||||
You can't declare functions or create regular expressions from within AngularJS expressions. This is
|
||||
to avoid complex model transformation logic inside templates. Such logic is better placed in a
|
||||
to avoid complex model transformation logic inside templates. Such logic is better placed in a
|
||||
controller or in a dedicated filter where it can be tested properly.
|
||||
|
||||
## `$event`
|
||||
@@ -277,7 +286,7 @@ result is a non-undefined value (see value stabilization algorithm below).
|
||||
</example>
|
||||
|
||||
|
||||
### Why this feature
|
||||
### Reasons for using one-time binding
|
||||
|
||||
The main purpose of one-time binding expression is to provide a way to create a binding
|
||||
that gets deregistered and frees up resources once the binding is stabilized.
|
||||
@@ -303,19 +312,23 @@ then the expression is not fulfilled and will remain watched.
|
||||
keep dirty-checking the watch in the future digest loops by following the same
|
||||
algorithm starting from step 1
|
||||
|
||||
#### Special case for object literals
|
||||
|
||||
Unlike simple values, object-literals are watched until every key is defined.
|
||||
See http://www.bennadel.com/blog/2760-one-time-data-bindings-for-object-literal-expressions-in-angularjs-1-3.htm
|
||||
|
||||
### How to benefit from one-time binding
|
||||
|
||||
If the expression will not change once set, it is a candidate for one-time binding.
|
||||
If the expression will not change once set, it is a candidate for one-time binding.
|
||||
Here are three example cases.
|
||||
|
||||
When interpolating text or attributes:
|
||||
|
||||
```html
|
||||
<div name="attr: {{::color}}">text: {{::name}}</div>
|
||||
<div name="attr: {{::color}}">text: {{::name | uppercase}}</div>
|
||||
```
|
||||
|
||||
When using a directive with bidirectional binding and the parameters will not change:
|
||||
When using a directive with bidirectional binding and parameters that will not change:
|
||||
|
||||
```js
|
||||
someModule.directive('someDirective', function() {
|
||||
@@ -338,7 +351,6 @@ When using a directive that takes an expression:
|
||||
|
||||
```html
|
||||
<ul>
|
||||
<li ng-repeat="item in ::items">{{item.name}};</li>
|
||||
<li ng-repeat="item in ::items | orderBy:'name'">{{item.name}};</li>
|
||||
</ul>
|
||||
```
|
||||
|
||||
|
||||
@@ -32,10 +32,13 @@ E.g. the markup `{{ 1234 | number:2 }}` formats the number 1234 with 2 decimal p
|
||||
|
||||
## Using filters in controllers, services, and directives
|
||||
|
||||
You can also use filters in controllers, services, and directives. For this, inject a dependency
|
||||
with the name `<filterName>Filter` to your controller/service/directive. E.g. using the dependency
|
||||
`numberFilter` will inject the number filter. The injected argument is a function that takes the
|
||||
value to format as first argument and filter parameters starting with the second argument.
|
||||
You can also use filters in controllers, services, and directives.
|
||||
|
||||
<div class="alert alert-info">
|
||||
For this, inject a dependency with the name `<filterName>Filter` into your controller/service/directive.
|
||||
E.g. a filter called `number` is injected by using the dependency `numberFilter`. The injected argument
|
||||
is a function that takes the value to format as first argument, and filter parameters starting with the second argument.
|
||||
</div>
|
||||
|
||||
The example below uses the filter called {@link ng.filter:filter `filter`}.
|
||||
This filter reduces arrays into sub arrays based on
|
||||
@@ -108,6 +111,7 @@ text upper-case.
|
||||
No filter: {{greeting}}<br>
|
||||
Reverse: {{greeting|reverse}}<br>
|
||||
Reverse + uppercase: {{greeting|reverse:true}}<br>
|
||||
Reverse, filtered in controller: {{filteredGreeting}}<br>
|
||||
</div>
|
||||
</file>
|
||||
|
||||
@@ -127,8 +131,9 @@ text upper-case.
|
||||
return out;
|
||||
};
|
||||
})
|
||||
.controller('MyController', ['$scope', function($scope) {
|
||||
.controller('MyController', ['$scope', 'reverseFilter', function($scope, reverseFilter) {
|
||||
$scope.greeting = 'hello';
|
||||
$scope.filteredGreeting = reverseFilter($scope.greeting);
|
||||
}]);
|
||||
</file>
|
||||
</example>
|
||||
|
||||
@@ -33,7 +33,7 @@ for other directives to augment its behavior.
|
||||
<input type="button" ng-click="reset()" value="Reset" />
|
||||
<input type="submit" ng-click="update(user)" value="Save" />
|
||||
</form>
|
||||
<pre>form = {{user | json}}</pre>
|
||||
<pre>user = {{user | json}}</pre>
|
||||
<pre>master = {{master | json}}</pre>
|
||||
</div>
|
||||
|
||||
@@ -95,6 +95,8 @@ and failing to satisfy its validity.
|
||||
<input type="button" ng-click="reset()" value="Reset" />
|
||||
<input type="submit" ng-click="update(user)" value="Save" />
|
||||
</form>
|
||||
<pre>user = {{user | json}}</pre>
|
||||
<pre>master = {{master | json}}</pre>
|
||||
</div>
|
||||
|
||||
<style type="text/css">
|
||||
@@ -183,6 +185,8 @@ didn't interact with a control
|
||||
<input type="button" ng-click="reset(form)" value="Reset" />
|
||||
<input type="submit" ng-click="update(user)" value="Save" />
|
||||
</form>
|
||||
<pre>user = {{user | json}}</pre>
|
||||
<pre>master = {{master | json}}</pre>
|
||||
</div>
|
||||
</file>
|
||||
|
||||
@@ -379,7 +383,7 @@ In the following example we create two directives:
|
||||
return {
|
||||
require: 'ngModel',
|
||||
link: function(scope, elm, attrs, ctrl) {
|
||||
var usernames = ['Jim', 'John', 'Jill', 'Jackie'];
|
||||
var usernames = ['Jim', 'John', 'Jill', 'Jackie'];
|
||||
|
||||
ctrl.$asyncValidators.username = function(modelValue, viewValue) {
|
||||
|
||||
@@ -491,9 +495,7 @@ The following example shows how to add two-way data-binding to contentEditable e
|
||||
link: function(scope, elm, attrs, ctrl) {
|
||||
// view -> model
|
||||
elm.on('blur', function() {
|
||||
scope.$apply(function() {
|
||||
ctrl.$setViewValue(elm.html());
|
||||
});
|
||||
ctrl.$setViewValue(elm.html());
|
||||
});
|
||||
|
||||
// model -> view
|
||||
|
||||
@@ -156,8 +156,94 @@ The syntax extension is based on a subset of the ICU MessageFormat syntax that c
|
||||
gender selections. Please refer to the links in the “Further Reading” section at the bottom of this
|
||||
section.
|
||||
|
||||
You may find it helpful to play with our [Plnkr Example](http://plnkr.co/edit/QBVRQ70dvKZDWmHW9RyR?p=preview)
|
||||
as you read the examples below.
|
||||
You may find it helpful to play with the following example as you read the explanations below:
|
||||
|
||||
<example name="message-format-example" module="messageFormatExample" deps="angular-message-format.js">
|
||||
<file name="index.html">
|
||||
<div ng-controller="ckCtrl">
|
||||
<b>Set number of recipients</b>
|
||||
<button ng-click="setNumRecipients(0)">None</button>
|
||||
<button ng-click="setNumRecipients(1)">One</button>
|
||||
<button ng-click="setNumRecipients(2)">Two</button>
|
||||
<button ng-click="setNumRecipients(3)">Three</button>
|
||||
|
||||
|
||||
<br><br>
|
||||
<b>Sender's</b> name: <input ng-model="sender.name">
|
||||
|
||||
<br><br><b>Recipients</b><br>
|
||||
<div ng-repeat="recipient in recipients">
|
||||
Name: <input ng-model="recipient.name">
|
||||
Gender: <button ng-click="setGender(recipient, 'male')">male</button>
|
||||
<button ng-click="setGender(recipient, 'female')">female</button>
|
||||
<button ng-click="setGender(recipient, 'other')">other</button>
|
||||
</div>
|
||||
|
||||
<br><br><b>Message</b><br>
|
||||
{{recipients.length, plural, offset:1
|
||||
=0 {You ({{sender.name}}) gave no gifts}
|
||||
=1 { {{ recipients[0].gender, select,
|
||||
male {You ({{sender.name}}) gave him ({{recipients[0].name}}) a gift.}
|
||||
female {You ({{sender.name}}) gave her ({{recipients[0].name}}) a gift.}
|
||||
other {You ({{sender.name}}) gave them ({{recipients[0].name}}) a gift.}
|
||||
}}
|
||||
}
|
||||
one { {{ recipients[0].gender, select,
|
||||
male {You ({{sender.name}}) gave him ({{recipients[0].name}}) and one other person a gift.}
|
||||
female {You ({{sender.name}}) gave her ({{recipients[0].name}}) and one other person a gift.}
|
||||
other {You ({{sender.name}}) gave them ({{recipients[0].name}}) and one other person a gift.}
|
||||
}}
|
||||
}
|
||||
other {You ({{sender.name}}) gave {{recipients.length}} people gifts. }
|
||||
}}
|
||||
|
||||
<br><br><b>In an attribute</b><br>
|
||||
<div attrib="{{recipients.length, plural, offset:1
|
||||
=0 {You ({{sender.name}}) gave no gifts}
|
||||
=1 { {{ recipients[0].gender, select,
|
||||
male {You ({{sender.name}}) gave him ({{recipients[0].name}}) a gift.}
|
||||
female {You ({{sender.name}}) gave her ({{recipients[0].name}}) a gift.}
|
||||
other {You ({{sender.name}}) gave them ({{recipients[0].name}}) a gift.}
|
||||
}}
|
||||
}
|
||||
one { {{ recipients[0].gender, select,
|
||||
male {You ({{sender.name}}) gave him ({{recipients[0].name}}) and one other person a gift.}
|
||||
female {You ({{sender.name}}) gave her ({{recipients[0].name}}) and one other person a gift.}
|
||||
other {You ({{sender.name}}) gave them ({{recipients[0].name}}) and one other person a gift.}
|
||||
}}
|
||||
}
|
||||
other {You ({{sender.name}}) gave {{recipients.length}} people gifts. }
|
||||
}}">
|
||||
This div has an attribute interpolated with messageformat. Use the DOM inspector to check it out.
|
||||
</div>
|
||||
</div>
|
||||
</file>
|
||||
<file name="app.js">
|
||||
function Person(name, gender) {
|
||||
this.name = name;
|
||||
this.gender = gender;
|
||||
}
|
||||
|
||||
angular.module('messageFormatExample', ['ngMessageFormat'])
|
||||
.controller('ckCtrl', function ($scope, $injector, $parse) {
|
||||
var people = [ new Person("Alice", "female"),
|
||||
new Person("Bob", "male"),
|
||||
new Person("Charlie", "male") ];
|
||||
|
||||
$scope.sender = new Person("Harry Potter", "male");
|
||||
$scope.recipients = people.slice();
|
||||
|
||||
$scope.setNumRecipients = function(n) {
|
||||
n = n > people.length ? people.length : n;
|
||||
$scope.recipients = people.slice(0, n);
|
||||
};
|
||||
|
||||
$scope.setGender = function(person, gender) {
|
||||
person.gender = gender;
|
||||
};
|
||||
});
|
||||
</file>
|
||||
</example>
|
||||
|
||||
### Plural Syntax
|
||||
|
||||
@@ -305,7 +391,7 @@ matching is **case-sensitive**.
|
||||
|
||||
#### Selection Keywords
|
||||
|
||||
Selection keywords are simple words like "male" and "female". The keyword, "other", and it's
|
||||
Selection keywords are simple words like "male" and "female". The keyword, "other", and its
|
||||
corresponding message are required while others are optional. It is used when the Angular
|
||||
expression does not match (case-insensitively) any of the other keywords specified.
|
||||
|
||||
@@ -333,9 +419,9 @@ allows you to nest plural and gender expressions in any order.
|
||||
Please note that if these are intended to reach a translator and be translated, it is recommended
|
||||
that the messages appear as a whole and not be split up.
|
||||
|
||||
### More complex example that demonstrates nesting
|
||||
### Demonstration of nesting
|
||||
|
||||
This is taken from the [plunker example](http://plnkr.co/edit/QBVRQ70dvKZDWmHW9RyR?p=preview) linked to earlier.
|
||||
This is taken from the above example.
|
||||
|
||||
```text
|
||||
{{recipients.length, plural, offset:1
|
||||
|
||||
@@ -53,7 +53,7 @@ In Angular applications, you move the job of filling page templates with data fr
|
||||
|
||||
## Specific Topics
|
||||
|
||||
* **Login: **[Google example](https://developers.google.com/+/photohunt/python), [AngularJS Faceb0ok library](https://github.com/pc035860/angular-easyfb), [Facebook example](http://blog.brunoscopelliti.com/facebook-authentication-in-your-angularjs-web-app), [authentication strategy](http://blog.brunoscopelliti.com/deal-with-users-authentication-in-an-angularjs-web-app), [unix-style authorization](http://frederiknakstad.com/authentication-in-single-page-applications-with-angular-js/)
|
||||
* **Login: **[Google example](https://developers.google.com/+/photohunt/python), [AngularJS Facebook library](https://github.com/pc035860/angular-easyfb), [Facebook example](http://blog.brunoscopelliti.com/facebook-authentication-in-your-angularjs-web-app), [authentication strategy](http://blog.brunoscopelliti.com/deal-with-users-authentication-in-an-angularjs-web-app), [unix-style authorization](http://frederiknakstad.com/authentication-in-single-page-applications-with-angular-js/)
|
||||
* **Mobile:** [Angular on Mobile Guide](http://www.ng-newsletter.com/posts/angular-on-mobile.html), [PhoneGap](http://devgirl.org/2013/06/10/quick-start-guide-phonegap-and-angularjs/)
|
||||
* **Other Languages:** [CoffeeScript](http://www.coffeescriptlove.com/2013/08/angularjs-and-coffeescript-tutorials.html), [Dart](https://github.com/angular/angular.dart.tutorial/wiki)
|
||||
* **Realtime: **[Socket.io](http://www.creativebloq.com/javascript/angularjs-collaboration-board-socketio-2132885), [OmniBinder](https://github.com/jeffbcross/omnibinder)
|
||||
|
||||
@@ -0,0 +1,142 @@
|
||||
@ngdoc overview
|
||||
@name Interpolation
|
||||
@sortOrder 275
|
||||
@description
|
||||
|
||||
# Interpolation and data-binding
|
||||
|
||||
Interpolation markup with embedded {@link guide/expression expressions} is used by Angular to
|
||||
provide data-binding to text nodes and attribute values.
|
||||
|
||||
An example of interpolation is shown below:
|
||||
|
||||
```html
|
||||
<a ng-href="img/{{username}}.jpg">Hello {{username}}!</a>
|
||||
```
|
||||
|
||||
### How text and attribute bindings work
|
||||
|
||||
During the compilation process the {@link ng.$compile compiler} uses the {@link ng.$interpolate $interpolate}
|
||||
service to see if text nodes and element attributes contain interpolation markup with embedded expressions.
|
||||
|
||||
If that is the case, the compiler adds an interpolateDirective to the node and
|
||||
registers {@link ng.$rootScope.Scope#$watch watches} on the computed interpolation function,
|
||||
which will update the corresponding text nodes or attribute values as part of the
|
||||
normal {@link ng.$rootScope.Scope#$digest digest} cycle.
|
||||
|
||||
Note that the interpolateDirective has a priority of 100 and sets up the watch in the preLink function.
|
||||
|
||||
### Binding to boolean attributes
|
||||
|
||||
Attributes such as `disabled` are called `boolean` attributes, because their presence means `true` and
|
||||
their absence means `false`. We cannot use normal attribute bindings with them, because the HTML
|
||||
specification does not require browsers to preserve the values of boolean attributes. This means that
|
||||
if we put an Angular interpolation expression into such an attribute then the binding information
|
||||
would be lost, because the browser ignores the attribute value.
|
||||
|
||||
In the following example, the interpolation information would be ignored and the browser would simply
|
||||
interpret the attribute as present, meaning that the button would always be disabled.
|
||||
|
||||
```html
|
||||
Disabled: <input type="checkbox" ng-model="isDisabled" />
|
||||
<button disabled="{{isDisabled}}">Disabled</button>
|
||||
```
|
||||
|
||||
For this reason, Angular provides special `ng`-prefixed directives for the following boolean attributes:
|
||||
{@link ngDisabled `disabled`}, {@link ngRequired `required`}, {@link ngSelected `selected`},
|
||||
{@link ngChecked `checked`}, {@link ngReadonly `readOnly`} , and {@link ngOpen `open`}.
|
||||
|
||||
These directives take an expression inside the attribute, and set the corresponding boolean attribute
|
||||
to true when the expression evaluates to truthy.
|
||||
|
||||
```html
|
||||
Disabled: <input type="checkbox" ng-model="isDisabled" />
|
||||
<button ng-disabled="isDisabled">Disabled</button>
|
||||
```
|
||||
|
||||
### `ngAttr` for binding to arbitrary attributes
|
||||
|
||||
Web browsers are sometimes picky about what values they consider valid for attributes.
|
||||
|
||||
For example, considering this template:
|
||||
|
||||
```html
|
||||
<svg>
|
||||
<circle cx="{{cx}}"></circle>
|
||||
</svg>
|
||||
```
|
||||
|
||||
We would expect Angular to be able to bind to this, but when we check the console we see
|
||||
something like `Error: Invalid value for attribute cx="{{cx}}"`. Because of the SVG DOM API's
|
||||
restrictions, you cannot simply write `cx="{{cx}}"`.
|
||||
|
||||
With `ng-attr-cx` you can work around this problem.
|
||||
|
||||
If an attribute with a binding is prefixed with the `ngAttr` prefix (denormalized as `ng-attr-`)
|
||||
then during the binding it will be applied to the corresponding unprefixed attribute. This allows
|
||||
you to bind to attributes that would otherwise be eagerly processed by browsers
|
||||
(e.g. an SVG element's `circle[cx]` attributes). When using `ngAttr`, the `allOrNothing` flag of
|
||||
{@link ng.$interpolate $interpolate} is used, so if any expression in the interpolated string
|
||||
results in `undefined`, the attribute is removed and not added to the element.
|
||||
|
||||
For example, we could fix the example above by instead writing:
|
||||
|
||||
```html
|
||||
<svg>
|
||||
<circle ng-attr-cx="{{cx}}"></circle>
|
||||
</svg>
|
||||
```
|
||||
|
||||
If one wants to modify a camelcased attribute (SVG elements have valid camelcased attributes),
|
||||
such as `viewBox` on the `svg` element, one can use underscores to denote that the attribute to bind
|
||||
to is naturally camelcased.
|
||||
|
||||
For example, to bind to `viewBox`, we can write:
|
||||
|
||||
```html
|
||||
<svg ng-attr-view_box="{{viewBox}}">
|
||||
</svg>
|
||||
```
|
||||
|
||||
The following attributes are also known to cause problems when used with normal bindings:
|
||||
|
||||
- **size** in `<select>` elements (see [Github issue 1619](https://github.com/angular/angular.js/issues/1619))
|
||||
- **placeholder** in `<textarea>` in Internet Explorer 10/11 (see [Github issue 5025](https://github.com/angular/angular.js/issues/5025))
|
||||
|
||||
|
||||
### Embedding interpolation markup inside expressions
|
||||
|
||||
Angular directives take either expressions or interpolation markup with embedded expressions. So the
|
||||
following example which embeds interpolation inside an expression is a bad practice:
|
||||
|
||||
```html
|
||||
<div ng-show="form{{$index}}.$invalid"></div>
|
||||
```
|
||||
|
||||
You should instead delegate the computation of complex expressions to the scope, like this:
|
||||
|
||||
```html
|
||||
<div ng-show="getForm($index).$invalid"></div>
|
||||
```
|
||||
|
||||
```js
|
||||
function getForm() {
|
||||
return $scope['form' + $index];
|
||||
}
|
||||
```
|
||||
|
||||
You can also access the `scope` with `this` in your templates:
|
||||
|
||||
```html
|
||||
<div ng-show="this['form' + $index].$invalid"></div>
|
||||
```
|
||||
|
||||
#### Why mixing interpolation and expressions is bad practice:
|
||||
|
||||
- It increases the complexity of the markup
|
||||
- There is no guarantee that it works for every directive, because interpolation itself is a directive.
|
||||
If another directive accesses attribute data before interpolation has run, it will get the raw
|
||||
interpolation markup and not data.
|
||||
- It impacts performance, as interpolation adds another watcher to the scope.
|
||||
- Since this is not recommended usage, we do not test for this, and changes to
|
||||
Angular core may break your code.
|
||||
@@ -3,17 +3,225 @@
|
||||
@sortOrder 550
|
||||
@description
|
||||
|
||||
# Migrating an App to a newer version
|
||||
|
||||
Minor version releases in AngularJS introduce several breaking changes that may require changes to your
|
||||
application's source code; for instance from 1.0 to 1.2 and from 1.2 to 1.3.
|
||||
|
||||
Although we try to avoid breaking changes, there are some cases where it is unavoidable.
|
||||
Although we try to avoid breaking changes, there are some cases where it is unavoidable:
|
||||
|
||||
* AngularJS has undergone thorough security reviews to make applications safer by default,
|
||||
which drives many of these changes.
|
||||
* Several new features, especially animations, would not be possible without a few changes.
|
||||
* Finally, some outstanding bugs were best fixed by changing an existing API.
|
||||
|
||||
# Migrating from 1.3 to 1.4
|
||||
<hr />
|
||||
|
||||
## Contents
|
||||
|
||||
<ul class="nav nav-list">
|
||||
<li>{@link guide/migration#migrating-from-1-4-to-1-5 Migrating from 1.4 to 1.5}</li>
|
||||
<li>{@link guide/migration#migrating-from-1-3-to-1-4 Migrating from 1.3 to 1.4}</li>
|
||||
<li>{@link guide/migration#migrating-from-1-2-to-1-3 Migrating from 1.2 to 1.3}</li>
|
||||
<li>{@link guide/migration#migrating-from-1-0-to-1-2 Migrating from 1.0 to 1.2}</li>
|
||||
</ul>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## Migrating from 1.4 to 1.5
|
||||
|
||||
Angular 1.5 takes a big step towards preparing developers for a smoother transition to Angular 2 in
|
||||
the future. Architecturing your applications using components, multi-slot transclusion, one-way
|
||||
bindings in isolate scopes, using lifecycle hooks in directive controllers and relying on native ES6
|
||||
features (such as classes and arrow functions) are now all possible with Angular 1.5.
|
||||
|
||||
|
||||
This release includes numerous bug and security fixes, as well as performance improvements to core
|
||||
services, directives, filters and helper functions. Existing applications can start enjoying the
|
||||
benefits of such changes in `$compile`, `$parse`, `$animate`, `$animateCss`, `$sanitize`, `ngOptions`,
|
||||
`currencyFilter`, `numberFilter`, `copy()` (to name but a few) without any change in code.
|
||||
|
||||
New features have been added to more than a dozen services, directives and filters across 8 modules.
|
||||
Among them, a few stand out:
|
||||
|
||||
* `angular.component()`: Introducing "components", a special sort of directive that are easy to
|
||||
configure and promote best practices (plus can bring Angular 1 applications closer to Angular 2's
|
||||
style of architecture).
|
||||
* Multi-slot transclusion: Enabling the design of more powerful and complex UI elements with a much
|
||||
simpler configuration and reduced boilerplate.
|
||||
* `$onInit` lifecycle hook: Introducing a new lifecycle hook for directive controllers, called after
|
||||
all required controllers have been constructed. This enables access to required controllers from
|
||||
a directive's controller, without having to rely on the linking function.
|
||||
* `ngAnimateSwap`: A new directive in `ngAnimate`, making it super easy to create rotating
|
||||
banner-like components.
|
||||
* Testing helpers: New helper functions in `ngMock`, simplifying testing for animations, component
|
||||
controllers and routing.
|
||||
|
||||
Also, notable is the improved support for ES6 features, such as classes and arrow functions. These
|
||||
features are now more reliably detected and correctly handled within the core.
|
||||
|
||||
|
||||
All this goodness doesn't come without a price, though. Below is a list of breaking changes (grouped
|
||||
by module) that need to be taken into account while migrating from 1.4. Fortunately, the majority of
|
||||
them should have a pretty low impact on most applications.
|
||||
|
||||
|
||||
### Core
|
||||
|
||||
We tried to keep the breaking changes inside the core components to a bare minimum. Still, a few of
|
||||
them were unavoidable.
|
||||
|
||||
#### Services (`$parse`)
|
||||
|
||||
Due to [0ea53503](https://github.com/angular/angular.js/commit/0ea535035a3a1a992948490c3533bffb83235052),
|
||||
a new special property, `$locals`, will be available for accessing the locals from an expression.
|
||||
This is a breaking change, only if a `$locals` property does already exist (and needs to be
|
||||
referenced) either on the `scope` or on the `locals` object. Your expressions should be changed to
|
||||
access such existing properties as `this.$locals` and `$locals.$locals` respectively.
|
||||
|
||||
|
||||
#### Directives (`ngOptions`)
|
||||
|
||||
A fair amount of work has been put into the `ngOptions` directive, fixing bugs and corner-cases and
|
||||
neutralizing browser quirks. A couple of breaking changes were made in the process:
|
||||
|
||||
Due to [b71d7c3f](https://github.com/angular/angular.js/commit/b71d7c3f3c04e65b02d88b33c22dd90ae3cdfc27),
|
||||
falsy values (`''`, `0`, `false` and `null`) are properly recognized as option group identifiers for
|
||||
options passed to `ngOptions`. Previously, all of these values were ignored and the option was not
|
||||
assigned to any group. `undefined` is still interpreted as "no group".
|
||||
If you have options with falsy group indentifiers that should still not be assigned to any group,
|
||||
then you must filter the values before passing them to `ngOptions`, converting falsy values to
|
||||
`undefined`.
|
||||
|
||||
Due to [ded25187](https://github.com/angular/angular.js/commit/ded2518756d4409fdfda0d4af243f2125bea01b5),
|
||||
`ngOptions` now explicitly requires `ngModel` on the same element, thus an error will be thrown if
|
||||
`ngModel` is not found. Previously, `ngOptions` would silently fail, which could lead to
|
||||
hard-to-debug errors.
|
||||
This is not expected to have any significant impact on applications, since `ngOptions` didn't work
|
||||
without `ngModel` before either. The main difference is that now it will fail with a more
|
||||
informative error message.
|
||||
|
||||
|
||||
#### Filters (`orderBy`)
|
||||
|
||||
Due to [2a85a634](https://github.com/angular/angular.js/commit/2a85a634f86c84f15b411ce009a3515fca7ba580),
|
||||
passing a non-array-like value (other than `undefined` or `null`) through the `orderBy` filter will
|
||||
throw an error. Previously, the input was returned unchanged, which could lead to hard-to-spot bugs
|
||||
and was not consistent with other filters (e.g. `filter`).
|
||||
Objects considered array-like include: arrays, array subclasses, strings, NodeLists,
|
||||
jqLite/jQuery collections
|
||||
|
||||
|
||||
### ngMessages (`ngMessage`)
|
||||
|
||||
Due to [4971ef12](https://github.com/angular/angular.js/commit/4971ef12d4c2c268cb8d26f90385dc96eba19db8),
|
||||
the `ngMessage` directive is now compiled with a priority of 1, which means directives on the same
|
||||
element as `ngMessage` with a priority lower than 1 will be applied when `ngMessage` calls its
|
||||
`$transclude` function. Previously, they were applied during the initial compile phase and were
|
||||
passed the comment element created by the transclusion of `ngMessage`.
|
||||
If you have custom directives that relied on the previous behavior, you need to give them a priority
|
||||
of 1 or greater.
|
||||
|
||||
|
||||
### ngResource (`$resource`)
|
||||
|
||||
The `$resource` service underwent a minor internal refactoring to finally solve a long-standing bug
|
||||
preventing requests from being cancelled using promises. Due to the nature of `$resource`'s
|
||||
configuration, it was not possible to follow the `$http` convention. A new `$cancelRequest()` method
|
||||
was introduced instead.
|
||||
|
||||
Due to [98528be3](https://github.com/angular/angular.js/commit/98528be311b48269ba0e15ba4e3e2ad9b89693a9),
|
||||
using a promise as `timeout` in `$resource` is no longer supported and will log a warning. This is
|
||||
hardly expected to affect the behavior of your application, since a promise as `timeout` didn't work
|
||||
before either, but it will now warn you explicitly when trying to pass one.
|
||||
If you need to be able to cancel pending requests, you can now use the new `$cancelRequest()` that
|
||||
will be available on `$resource` instances.
|
||||
|
||||
|
||||
### ngRoute (`ngView`)
|
||||
|
||||
Due to [983b0598](https://github.com/angular/angular.js/commit/983b0598121a8c5a3a51a30120e114d7e3085d4d),
|
||||
a new property will be available on the scope of the route, allowing easy access to the route's
|
||||
resolved values from the view's template. The default name for this property is `$resolve`. This is
|
||||
a breaking change, only if a `$resolve` property is already available on the scope, in which case
|
||||
the existing property will be hidden or overwritten.
|
||||
To fix this, you should choose a custom name for this property, that does not collide with other
|
||||
properties on the scope, by specifying the `resolveAs` property on the route.
|
||||
|
||||
|
||||
### ngSanitize (`$sanitize`, `linky`)
|
||||
|
||||
The HTML sanitizer has been re-implemented using inert documents, increasing security, fixing some
|
||||
corner-cases that were difficult to handle and reducing its size by about 20% (in terms of loc). In
|
||||
order to make it more secure by default, a couple of breaking changes have been introduced:
|
||||
|
||||
Due to [181fc567](https://github.com/angular/angular.js/commit/181fc567d873df065f1e84af7225deb70a8d2eb9),
|
||||
SVG support in `$sanitize` is now an opt-in feature (i.e. disabled by default), as it could make
|
||||
an application vulnerable to click-hijacking attacks. If your application relies on it, you can
|
||||
still turn it on with `$sanitizeProvider.enableSvg(true)`, but you extra precautions need to be
|
||||
taken in order to keep your application secure. Read the documentation for more information about
|
||||
the dangers and ways to mitigate them.
|
||||
|
||||
Due to [7a668cdd](https://github.com/angular/angular.js/commit/7a668cdd7d08a7016883eb3c671cbcd586223ae8),
|
||||
the `$sanitize` service will now remove instances of the `<use>` tag from the content passed to it.
|
||||
This element is used to import external SVG resources, which is a security risk as the `$sanitize`
|
||||
service does not have access to the resource in order to sanitize it.
|
||||
|
||||
Similarly, due to [234053fc](https://github.com/angular/angular.js/commit/234053fc9ad90e0d05be7e8359c6af66be94c094),
|
||||
the `$sanitize` service will now also remove instances of the `usemap` attribute from any elements
|
||||
passed to it. This attribute is used to reference another element by `name` or `id`. Since the
|
||||
`name` and `id` attributes are already blacklisted, a sanitized `usemap` attribute could only
|
||||
reference unsanitized content, which is a security risk.
|
||||
|
||||
Due to [98c2db7f](https://github.com/angular/angular.js/commit/98c2db7f9c2d078a408576e722407d518c7ee10a),
|
||||
passing a non-string value (other than `undefined` or `null`) through the `linky` filter will throw
|
||||
an error. This is not expected to have any significant impact on applications, since the input was
|
||||
always assumed to be of type 'string', so passing non-string values never worked correctly anyway.
|
||||
The main difference is that now it will fail faster and with a more informative error message.
|
||||
|
||||
|
||||
## ngTouch (`ngClick`)
|
||||
|
||||
Due to [0dfc1dfe](https://github.com/angular/angular.js/commit/0dfc1dfebf26af7f951f301c4e3848ac46f05d7f),
|
||||
the `ngClick` override directive from the `ngTouch` module is **deprecated and disabled by default**.
|
||||
This means that on touch-based devices, users might now experience a 300ms delay before a click
|
||||
event is fired.
|
||||
|
||||
If you rely on this directive, you can still enable it using
|
||||
`$touchProvider.ngClickOverrideEnabled()`:
|
||||
|
||||
```js
|
||||
angular.module('myApp').config(function($touchProvider) {
|
||||
$touchProvider.ngClickOverrideEnabled(true);
|
||||
});
|
||||
```
|
||||
|
||||
Going forward, we recommend using [FastClick](https://github.com/ftlabs/fastclick) or perhaps one of
|
||||
the [Angular 3rd party touch-related modules](http://ngmodules.org/tags/touch) that provide similar
|
||||
functionality.
|
||||
|
||||
Also note that modern browsers already remove the 300ms delay under some circumstances:
|
||||
|
||||
- **Chrome and Firefox for Android** remove the 300ms delay when the well-known
|
||||
`<meta name="viewport" content="width=device-width">` is set.
|
||||
- **Internet Explorer** removes the delay, when the `touch-action` css property is set to `none` or
|
||||
`manipulation`.
|
||||
- Since **iOS 8, Safari** removes the delay on so-called "slow taps".
|
||||
|
||||
For more info on the topic, you can take a look at this
|
||||
[article by Telerik](http://developer.telerik.com/featured/300-ms-click-delay-ios-8/).
|
||||
|
||||
<div class="alert alert-warning">
|
||||
**Note:** This change does **not** affect the `ngSwipe` directive.
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## Migrating from 1.3 to 1.4
|
||||
|
||||
Angular 1.4 fixes major animation issues and introduces a new API for `ngCookies`. Further, there
|
||||
are changes to `ngMessages`, `$compile`, `ngRepeat`, `ngOptions `and some fixes to core filters:
|
||||
@@ -37,13 +245,13 @@ relatively straightforward otherwise.
|
||||
|
||||
|
||||
|
||||
## Animation (`ngAnimate`)
|
||||
### Animation (`ngAnimate`)
|
||||
|
||||
Animations in 1.4 have been refactored internally, but the API has stayed much the same. There are, however,
|
||||
some breaking changes that need to be addressed when upgrading to 1.4.
|
||||
|
||||
Due to [c8700f04](https://github.com/angular/angular.js/commit/c8700f04fb6fb5dc21ac24de8665c0476d6db5ef),
|
||||
JavaSript and CSS animations can no longer be run in
|
||||
JavaScript and CSS animations can no longer be run in
|
||||
parallel. With earlier versions of ngAnimate, both CSS and JS animations
|
||||
would be run together when multiple animations were detected. This
|
||||
feature has been removed, however, the same effect, with even more
|
||||
@@ -88,10 +296,10 @@ element.on('$animate:before', function(e, data) {
|
||||
element.off('$animate:before', fn);
|
||||
|
||||
// 1.4+
|
||||
$animate.on(element, 'enter', function(data) {
|
||||
$animate.on('enter', element, function(data) {
|
||||
//...
|
||||
});
|
||||
$animate.off(element, 'enter', fn);
|
||||
$animate.off('enter', element, fn);
|
||||
```
|
||||
|
||||
Due to [c8700f04](https://github.com/angular/angular.js/commit/c8700f04fb6fb5dc21ac24de8665c0476d6db5ef),
|
||||
@@ -136,9 +344,9 @@ class based animations (animations triggered via ngClass) in order to ensure tha
|
||||
|
||||
|
||||
|
||||
## Forms (`ngMessages`, `ngOptions`)
|
||||
### Forms (`ngMessages`, `ngOptions`, `select`)
|
||||
|
||||
### ngMessages
|
||||
#### ngMessages
|
||||
The ngMessages module has also been subject to an internal refactor to allow it to be more flexible
|
||||
and compatible with dynamic message data. The `ngMessage` directive now supports a new attribute
|
||||
called `ng-message-exp` which will evaluate an expression and will keep track of that expression
|
||||
@@ -170,7 +378,26 @@ other inline messages situated as children within the `ngMessages` container dir
|
||||
Depending on where the `ngMessagesInclude` directive is placed it will be prioritized inline with the other messages
|
||||
before and after it.
|
||||
|
||||
### ngOptions
|
||||
Also due to [c9a4421f](https://github.com/angular/angular.js/commit/c9a4421fc3c97448527eadef1f42eb2f487ec2e0),
|
||||
it is no longer possible to use interpolation inside the `ngMessages` attribute expression. This technique
|
||||
is generally not recommended, and can easily break when a directive implementation changes. In cases
|
||||
where a simple expression is not possible, you can delegate accessing the object to a function:
|
||||
|
||||
```html
|
||||
<div ng-messages="ctrl.form['field_{{$index}}'].$error">...</div>
|
||||
```
|
||||
would become
|
||||
```html
|
||||
<div ng-messages="ctrl.getMessages($index)">...</div>
|
||||
```
|
||||
where `ctrl.getMessages()`
|
||||
```javascript
|
||||
ctrl.getMessages = function($index) {
|
||||
return ctrl.form['field_' + $index].$error;
|
||||
}
|
||||
```
|
||||
|
||||
#### ngOptions
|
||||
|
||||
The `ngOptions` directive has also been refactored and as a result some long-standing bugs
|
||||
have been fixed. The breaking changes are comparatively minor and should not affect most applications.
|
||||
@@ -178,8 +405,8 @@ have been fixed. The breaking changes are comparatively minor and should not aff
|
||||
Due to [7fda214c](https://github.com/angular/angular.js/commit/7fda214c4f65a6a06b25cf5d5aff013a364e9cef),
|
||||
when `ngOptions` renders the option values within the DOM, the resulting HTML code is different.
|
||||
Normally this should not affect your application at all, however, if your code relies on inspecting
|
||||
the value property of `<option>` elements (that `ngOptions` generates) then be sure to [read the details]
|
||||
(https://github.com/angular/angular.js/commit/7fda214c4f65a6a06b25cf5d5aff013a364e9cef).
|
||||
the value property of `<option>` elements (that `ngOptions` generates) then be sure
|
||||
to [read the details](https://github.com/angular/angular.js/commit/7fda214c4f65a6a06b25cf5d5aff013a364e9cef).
|
||||
|
||||
Due to [7fda214c](https://github.com/angular/angular.js/commit/7fda214c4f65a6a06b25cf5d5aff013a364e9cef),
|
||||
when iterating over an object's properties using the `(key, value) in obj` syntax
|
||||
@@ -189,10 +416,45 @@ But in practice this is not what people want and so this change iterates over pr
|
||||
in the order they are returned by Object.keys(obj), which is almost always the order
|
||||
in which the properties were defined.
|
||||
|
||||
Also due to [7fda214c](https://github.com/angular/angular.js/commit/7fda214c4f65a6a06b25cf5d5aff013a364e9cef),
|
||||
setting the ngOptions attribute expression after the element is compiled, will no longer trigger the ngOptions behavior.
|
||||
This worked previously because the ngOptions logic was part of the select directive, while
|
||||
it is now implemented in the ngOptions directive itself.
|
||||
|
||||
## Templating (`ngRepeat`, `$compile`)
|
||||
#### select
|
||||
|
||||
### ngRepeat
|
||||
Due to [7fda214c](https://github.com/angular/angular.js/commit/7fda214c4f65a6a06b25cf5d5aff013a364e9cef),
|
||||
the `select` directive will now use strict comparison of the `ngModel` scope value against `option`
|
||||
values to determine which option is selected. This means non-string scope values (such as `Number` or `Boolean`)
|
||||
will not be matched against equivalent option strings (such as the strings `"123"`, `"true"` or `"false"`).
|
||||
|
||||
In Angular 1.3.x, setting `scope.x = 200` would select the option with the value 200 in the following `select`:
|
||||
|
||||
```
|
||||
<select ng-model="x">
|
||||
<option value="100">100</option>
|
||||
<option value="200">200</option>
|
||||
</select>
|
||||
```
|
||||
|
||||
In Angular 1.4.x, the 'unknown option' will be selected.
|
||||
|
||||
To remedy this, you can initialize the model as a string: `scope.x = '200'`, or if you want to
|
||||
keep the model as a `Number`, you can do the conversion via `$formatters` and `$parsers` on `ngModel`:
|
||||
|
||||
```js
|
||||
ngModelCtrl.$parsers.push(function(value) {
|
||||
return parseInt(value, 10); // Convert option value to number
|
||||
});
|
||||
|
||||
ngModelCtrl.$formatters.push(function(value) {
|
||||
return value.toString(); // Convert scope value to string
|
||||
});
|
||||
```
|
||||
|
||||
### Templating (`ngRepeat`, `$compile`)
|
||||
|
||||
#### ngRepeat
|
||||
|
||||
Due to [c260e738](https://github.com/angular/angular.js/commit/c260e7386391877625eda086480de73e8a0ba921),
|
||||
previously, the order of items when using ngRepeat to iterate over object properties was guaranteed to be consistent
|
||||
@@ -211,15 +473,18 @@ https://github.com/petebacondarwin/angular-toArrayFilter
|
||||
or some other mechanism, and then sort them manually in the order you need.
|
||||
|
||||
|
||||
### $compile
|
||||
#### $compile
|
||||
|
||||
Due to [6a38dbfd](https://github.com/angular/angular.js/commit/6a38dbfd3c34c8f9efff503d17eb3cbeb666d422),
|
||||
previously, '&' expressions would always set up a function in the isolate scope. Now, if the binding
|
||||
is marked as optional and the attribute is not specified, no function will be added to the isolate scope.
|
||||
|
||||
Due to [62d514b](https://github.com/angular/angular.js/commit/62d514b06937cc7dd86e973ea11165c88343b42d),
|
||||
returning an object from a controller constructor function will now override the scope. Views that use the
|
||||
controllerAs method will no longer get the this reference, but the returned object.
|
||||
|
||||
|
||||
## Cookies (`ngCookies`)
|
||||
### Cookies (`ngCookies`)
|
||||
|
||||
Due to [38fbe3ee](https://github.com/angular/angular.js/commit/38fbe3ee8370fc449b82d80df07b5c2ed2cd5fbe),
|
||||
`$cookies` will no longer expose properties that represent the current browser cookie
|
||||
@@ -258,7 +523,7 @@ delegates calls.
|
||||
|
||||
|
||||
|
||||
## Server Requests (`$http`)
|
||||
### Server Requests (`$http`)
|
||||
|
||||
Due to [5da1256](https://github.com/angular/angular.js/commit/5da1256fc2812d5b28fb0af0de81256054856369),
|
||||
`transformRequest` functions can no longer modify request headers.
|
||||
@@ -291,9 +556,9 @@ $http.get(url, {
|
||||
|
||||
|
||||
|
||||
## Filters (`filter`, `limitTo`)
|
||||
### Filters (`filter`, `limitTo`)
|
||||
|
||||
### `filter` filter
|
||||
#### `filter` filter
|
||||
Due to [cea8e751](https://github.com/angular/angular.js/commit/cea8e75144e6910b806b63a6ec2a6d118316fddd),
|
||||
the `filter` filter will throw an error when used with a non-array. Beforehand it would silently
|
||||
return an empty array.
|
||||
@@ -301,7 +566,7 @@ return an empty array.
|
||||
If necessary, this can be worked around by converting an object to an array,
|
||||
using a filter such as https://github.com/petebacondarwin/angular-toArrayFilter.
|
||||
|
||||
### `limitTo` filter
|
||||
#### `limitTo` filter
|
||||
Due to [a3c3bf33](https://github.com/angular/angular.js/commit/a3c3bf3332e5685dc319c46faef882cb6ac246e1),
|
||||
the limitTo filter has changed behavior when the provided limit value is invalid.
|
||||
Now, instead of returning empty object/array, it returns unchanged input.
|
||||
@@ -310,9 +575,9 @@ Now, instead of returning empty object/array, it returns unchanged input.
|
||||
|
||||
|
||||
|
||||
# Migrating from 1.2 to 1.3
|
||||
## Migrating from 1.2 to 1.3
|
||||
|
||||
## Controllers
|
||||
### Controllers
|
||||
|
||||
Due to [3f2232b5](https://github.com/angular/angular.js/commit/3f2232b5a181512fac23775b1df4a6ebda67d018),
|
||||
`$controller` will no longer look for controllers on `window`.
|
||||
@@ -350,7 +615,7 @@ angular.module('myModule').config(['$controllerProvider', function($controllerPr
|
||||
}]);
|
||||
```
|
||||
|
||||
## Angular Expression Parsing (`$parse` + `$interpolate`)
|
||||
### Angular Expression Parsing (`$parse` + `$interpolate`)
|
||||
|
||||
- due to [77ada4c8](https://github.com/angular/angular.js/commit/77ada4c82d6b8fc6d977c26f3cdb48c2f5fbe5a5),
|
||||
|
||||
@@ -408,7 +673,7 @@ expression parser; there are six of them: false, null, undefined, NaN, 0 and "".
|
||||
|
||||
|
||||
|
||||
## Miscellaneous Angular helpers
|
||||
### Miscellaneous Angular helpers
|
||||
|
||||
- **Angular.copy:** due to [b59b04f9](https://github.com/angular/angular.js/commit/b59b04f98a0b59eead53f6a53391ce1bbcbe9b57),
|
||||
|
||||
@@ -439,15 +704,14 @@ This change also makes our forEach behave more like Array#forEach.
|
||||
|
||||
|
||||
- **angular.toJson:** due to [c054288c](https://github.com/angular/angular.js/commit/c054288c9722875e3595e6e6162193e0fb67a251),
|
||||
|
||||
If you expected `toJson` to strip these types of properties before, you will have to
|
||||
manually do this yourself now.
|
||||
`toJson()` will no longer strip properties starting with a single `$`. If you relied on
|
||||
`toJson()`'s stripping these types of properties before, you will have to do it manually now.
|
||||
It will still strip properties starting with `$$` though.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## jqLite / JQuery
|
||||
### jqLite / JQuery
|
||||
|
||||
- **jqLite:** due to [a196c8bc](https://github.com/angular/angular.js/commit/a196c8bca82a28c08896d31f1863cf4ecd11401c),
|
||||
previously it was possible to set jqLite data on Text/Comment
|
||||
@@ -463,7 +727,7 @@ jQuery. We don't expect that app code actually depends on this accidental featur
|
||||
|
||||
|
||||
|
||||
## Angular HTML Compiler (`$compile`)
|
||||
### Angular HTML Compiler (`$compile`)
|
||||
|
||||
|
||||
- due to [2ee29c5d](https://github.com/angular/angular.js/commit/2ee29c5da81ffacdc1cabb438f5d125d5e116cb9),
|
||||
@@ -527,10 +791,40 @@ After:
|
||||
};
|
||||
});
|
||||
|
||||
- due to [531a8de7](https://github.com/angular/angular.js/commit/531a8de72c439d8ddd064874bf364c00cedabb11),
|
||||
`$observe` no longer registers on undefined attributes. For example, if you were using `$observe` on
|
||||
an absent optional attribute to set a default value, the following would not work anymore:
|
||||
|
||||
```html
|
||||
<my-dir></my-dir>
|
||||
```
|
||||
|
||||
```js
|
||||
// Link function for directive myDir
|
||||
link: function(scope, element, attr) {
|
||||
attr.$observe('myAttr', function(newVal) {
|
||||
scope.myValue = newVal ? newVal : 'myDefaultValue';
|
||||
})
|
||||
}
|
||||
```
|
||||
|
||||
Instead, check if the attribute is set before registering the observer:
|
||||
|
||||
```js
|
||||
link: function(scope, element, attr) {
|
||||
if (attr.myAttr) {
|
||||
// register the observer
|
||||
} else {
|
||||
// set the default
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
|
||||
|
||||
## Forms, Inputs and ngModel
|
||||
|
||||
|
||||
### Forms, Inputs and ngModel
|
||||
|
||||
- due to [1be9bb9d](https://github.com/angular/angular.js/commit/1be9bb9d3527e0758350c4f7417a4228d8571440),
|
||||
|
||||
@@ -599,11 +893,18 @@ $scope.resetWithCancel = function (e) {
|
||||
[#5864](https://github.com/angular/angular.js/issues/5864))
|
||||
|
||||
|
||||
- {@link input[checkbox] `input[checkbox]`} now supports constant expressions in `ngTrueValue` and
|
||||
`ngFalseValue`, making it now possible to e.g. use boolean and integer values. Previously, these attributes would
|
||||
always be treated as strings, whereas they are now parsed as expressions, and will throw if an expression
|
||||
is non-constant. To convert non-constant strings into constant expressions, simply wrap them in an
|
||||
extra pair of quotes, like so:
|
||||
|
||||
`<input type="checkbox" ng-model="..." ng-true-value="'truthyValue'">`
|
||||
|
||||
See [c90cefe1614](https://github.com/angular/angular.js/commit/c90cefe16142d973a123e945fc9058e8a874c357)
|
||||
|
||||
|
||||
|
||||
|
||||
## Scopes and Digests (`$scope`)
|
||||
### Scopes and Digests (`$scope`)
|
||||
|
||||
- due to [8c6a8171](https://github.com/angular/angular.js/commit/8c6a8171f9bdaa5cdabc0cc3f7d3ce10af7b434d),
|
||||
Scope#$id is now of type number rather than string. Since the
|
||||
@@ -623,7 +924,7 @@ anyone.
|
||||
|
||||
|
||||
|
||||
## Server Requests (`$http`, `$resource`)
|
||||
### Server Requests (`$http`, `$resource`)
|
||||
- **$http:** due to [ad4336f9](https://github.com/angular/angular.js/commit/ad4336f9359a073e272930f8f9bcd36587a8648f),
|
||||
|
||||
|
||||
@@ -690,7 +991,7 @@ More details on the new interceptors API (which has been around as of v1.1.4) ca
|
||||
|
||||
|
||||
|
||||
## Modules and Injector (`$inject`)
|
||||
### Modules and Injector (`$inject`)
|
||||
|
||||
- due to [c0b4e2db](https://github.com/angular/angular.js/commit/c0b4e2db9cbc8bc3164cedc4646145d3ab72536e),
|
||||
|
||||
@@ -732,7 +1033,7 @@ app. This is no longer possible within a single module.
|
||||
|
||||
|
||||
|
||||
## Animation (`ngAnimate`)
|
||||
### Animation (`ngAnimate`)
|
||||
|
||||
|
||||
- due to [1cb8584e](https://github.com/angular/angular.js/commit/1cb8584e8490ecdb1b410a8846c4478c6c2c0e53),
|
||||
@@ -785,7 +1086,7 @@ After:
|
||||
Please view the documentation for ngAnimate for more info.
|
||||
|
||||
|
||||
## Testing
|
||||
### Testing
|
||||
|
||||
- due to [85880a64](https://github.com/angular/angular.js/commit/85880a64900fa22a61feb926bf52de0965332ca5), some deprecated features of
|
||||
Protractor tests no longer work.
|
||||
@@ -824,7 +1125,7 @@ or simply use:
|
||||
var el = element(by.repeater('foo in foos').row(2))
|
||||
|
||||
|
||||
## Internet Explorer 8
|
||||
### Internet Explorer 8
|
||||
|
||||
- due to [eaa1d00b](https://github.com/angular/angular.js/commit/eaa1d00b24008f590b95ad099241b4003688cdda),
|
||||
As communicated before, IE8 is no longer supported.
|
||||
@@ -834,7 +1135,7 @@ or simply use:
|
||||
|
||||
|
||||
|
||||
# Migrating from 1.0 to 1.2
|
||||
## Migrating from 1.0 to 1.2
|
||||
|
||||
|
||||
<div class="alert alert-warning">
|
||||
@@ -877,7 +1178,7 @@ below should still apply, but you may want to consult the
|
||||
</ul>
|
||||
|
||||
|
||||
## ngRoute has been moved into its own module
|
||||
### ngRoute has been moved into its own module
|
||||
|
||||
Just like `ngResource`, `ngRoute` is now its own module.
|
||||
|
||||
@@ -908,7 +1209,7 @@ var myApp = angular.module('myApp', ['ngRoute', 'someOtherModule']);
|
||||
See [5599b55b](https://github.com/angular/angular.js/commit/5599b55b04788c2e327d7551a4a699d75516dd21).
|
||||
|
||||
|
||||
## Templates no longer automatically unwrap promises
|
||||
### Templates no longer automatically unwrap promises
|
||||
|
||||
`$parse` and templates in general will no longer automatically unwrap promises.
|
||||
|
||||
@@ -942,7 +1243,7 @@ See [5dc35b52](https://github.com/angular/angular.js/commit/5dc35b527b3c99f6544b
|
||||
[b6a37d11](https://github.com/angular/angular.js/commit/b6a37d112b3e1478f4d14a5f82faabf700443748).
|
||||
|
||||
|
||||
## Syntax for named wildcard parameters changed in `$route`
|
||||
### Syntax for named wildcard parameters changed in `$route`
|
||||
|
||||
To migrate the code, follow the example below. Here, `*highlight` becomes `:highlight*`
|
||||
|
||||
@@ -963,7 +1264,7 @@ $routeProvider.when('/Book1/:book/Chapter/:chapter/:highlight*/edit',
|
||||
See [04cebcc1](https://github.com/angular/angular.js/commit/04cebcc133c8b433a3ac5f72ed19f3631778142b).
|
||||
|
||||
|
||||
## You can only bind one expression to `*[src]`, `*[ng-src]` or `action`
|
||||
### You can only bind one expression to `*[src]`, `*[ng-src]` or `action`
|
||||
|
||||
With the exception of `<a>` and `<img>` elements, you cannot bind more than one expression to the
|
||||
`src` or `action` attribute of elements.
|
||||
@@ -1038,7 +1339,7 @@ scope.getIframeSrc = function() {
|
||||
See [38deedd6](https://github.com/angular/angular.js/commit/38deedd6e3d806eb8262bb43f26d47245f6c2739).
|
||||
|
||||
|
||||
## Interpolations inside DOM event handlers are now disallowed
|
||||
### Interpolations inside DOM event handlers are now disallowed
|
||||
|
||||
DOM event handlers execute arbitrary Javascript code. Using an interpolation for such handlers
|
||||
means that the interpolated value is a JS string that is evaluated. Storing or generating such
|
||||
@@ -1065,7 +1366,7 @@ HTML: <div ng-click="foo()">
|
||||
See [39841f2e](https://github.com/angular/angular.js/commit/39841f2ec9b17b3b2920fd1eb548d444251f4f56).
|
||||
|
||||
|
||||
## Directives cannot end with -start or -end
|
||||
### Directives cannot end with -start or -end
|
||||
|
||||
This change was necessary to enable multi-element directives. The best fix is to rename existing
|
||||
directives so that they don't end with these suffixes.
|
||||
@@ -1073,7 +1374,7 @@ directives so that they don't end with these suffixes.
|
||||
See [e46100f7](https://github.com/angular/angular.js/commit/e46100f7097d9a8f174bdb9e15d4c6098395c3f2).
|
||||
|
||||
|
||||
## In $q, promise.always has been renamed promise.finally
|
||||
### In $q, promise.always has been renamed promise.finally
|
||||
|
||||
The reason for this change is to align `$q` with the [Q promise
|
||||
library](https://github.com/kriskowal/q), despite the fact that this makes it a bit more difficult
|
||||
@@ -1105,7 +1406,7 @@ $http.get('/foo')['finally'](doSomething);
|
||||
See [f078762d](https://github.com/angular/angular.js/commit/f078762d48d0d5d9796dcdf2cb0241198677582c).
|
||||
|
||||
|
||||
## ngMobile is now ngTouch
|
||||
### ngMobile is now ngTouch
|
||||
|
||||
Many touch-enabled devices are not mobile devices, so we decided to rename this module to better
|
||||
reflect its concerns.
|
||||
@@ -1116,7 +1417,7 @@ To migrate, replace all references to `ngMobile` with `ngTouch` and `angular-mob
|
||||
See [94ec84e7](https://github.com/angular/angular.js/commit/94ec84e7b9c89358dc00e4039009af9e287bbd05).
|
||||
|
||||
|
||||
## resource.$then has been removed
|
||||
### resource.$then has been removed
|
||||
|
||||
Resource instances do not have a `$then` function anymore. Use the `$promise.then` instead.
|
||||
|
||||
@@ -1135,7 +1436,7 @@ Resource.query().$promise.then(callback);
|
||||
See [05772e15](https://github.com/angular/angular.js/commit/05772e15fbecfdc63d4977e2e8839d8b95d6a92d).
|
||||
|
||||
|
||||
## Resource methods return the promise
|
||||
### Resource methods return the promise
|
||||
|
||||
Methods of a resource instance return the promise rather than the instance itself.
|
||||
|
||||
@@ -1155,7 +1456,7 @@ resource.chaining = true;
|
||||
See [05772e15](https://github.com/angular/angular.js/commit/05772e15fbecfdc63d4977e2e8839d8b95d6a92d).
|
||||
|
||||
|
||||
## Resource promises are resolved with the resource instance
|
||||
### Resource promises are resolved with the resource instance
|
||||
|
||||
On success, the resource promise is resolved with the resource instance rather than HTTP response object.
|
||||
|
||||
@@ -1186,7 +1487,7 @@ var Resource = $resource('/url', {}, {
|
||||
See [05772e15](https://github.com/angular/angular.js/commit/05772e15fbecfdc63d4977e2e8839d8b95d6a92d).
|
||||
|
||||
|
||||
## $location.search supports multiple keys
|
||||
### $location.search supports multiple keys
|
||||
|
||||
{@link ng.$location#search `$location.search`} now supports multiple keys with the
|
||||
same value provided that the values are stored in an array.
|
||||
@@ -1203,7 +1504,7 @@ passing it to `$location`.
|
||||
See [80739409](https://github.com/angular/angular.js/commit/807394095b991357225a03d5fed81fea5c9a1abe).
|
||||
|
||||
|
||||
## ngBindHtmlUnsafe has been removed and replaced by ngBindHtml
|
||||
### ngBindHtmlUnsafe has been removed and replaced by ngBindHtml
|
||||
|
||||
`ngBindHtml` provides `ngBindHtmlUnsafe` like
|
||||
behavior (evaluate an expression and innerHTML the result into the DOM) when bound to the result
|
||||
@@ -1219,7 +1520,7 @@ trusted.
|
||||
See [dae69473](https://github.com/angular/angular.js/commit/dae694739b9581bea5dbc53522ec00d87b26ae55).
|
||||
|
||||
|
||||
## Form names that are expressions are evaluated
|
||||
### Form names that are expressions are evaluated
|
||||
|
||||
If you have form names that will evaluate as an expression:
|
||||
|
||||
@@ -1251,7 +1552,7 @@ Supporting the previous behavior offers no benefit.
|
||||
See [8ea802a1](https://github.com/angular/angular.js/commit/8ea802a1d23ad8ecacab892a3a451a308d9c39d7).
|
||||
|
||||
|
||||
## hasOwnProperty disallowed as an input name
|
||||
### hasOwnProperty disallowed as an input name
|
||||
|
||||
Inputs with name equal to `hasOwnProperty` are not allowed inside form or ngForm directives.
|
||||
|
||||
@@ -1262,7 +1563,7 @@ and bad practice. To migrate, change your input name.
|
||||
See [7a586e5c](https://github.com/angular/angular.js/commit/7a586e5c19f3d1ecc3fefef084ce992072ee7f60).
|
||||
|
||||
|
||||
## Directives: Order of postLink functions reversed
|
||||
### Directives: Order of postLink functions reversed
|
||||
|
||||
The order of postLink fn is now mirror opposite of the order in which corresponding preLinking and compile functions execute.
|
||||
|
||||
@@ -1318,7 +1619,7 @@ attribute interpolation directive was adjusted.
|
||||
See [31f190d4](https://github.com/angular/angular.js/commit/31f190d4d53921d32253ba80d9ebe57d6c1de82b).
|
||||
|
||||
|
||||
## Directive priority
|
||||
### Directive priority
|
||||
|
||||
the priority of ngRepeat, ngSwitchWhen, ngIf, ngInclude and ngView has changed. This could affect directives that explicitly specify their priority.
|
||||
|
||||
@@ -1336,7 +1637,7 @@ ngView | 1000 | 400
|
||||
See [b7af76b4](https://github.com/angular/angular.js/commit/b7af76b4c5aa77648cc1bfd49935b48583419023).
|
||||
|
||||
|
||||
## ngScenario
|
||||
### ngScenario
|
||||
|
||||
browserTrigger now uses an eventData object instead of direct parameters for mouse events.
|
||||
To migrate, place the `keys`,`x` and `y` parameters inside of an object and place that as the
|
||||
@@ -1345,7 +1646,7 @@ third parameter for the browserTrigger function.
|
||||
See [28f56a38](https://github.com/angular/angular.js/commit/28f56a383e9d1ff378e3568a3039e941c7ffb1d8).
|
||||
|
||||
|
||||
## ngInclude and ngView replace its entire element on update
|
||||
### ngInclude and ngView replace its entire element on update
|
||||
|
||||
Previously `ngInclude` and `ngView` only updated its element's content. Now these directives will
|
||||
recreate the element every time a new content is included.
|
||||
@@ -1357,7 +1658,7 @@ See [7d69d52a](https://github.com/angular/angular.js/commit/7d69d52acff8578e0f7d
|
||||
[aa2133ad](https://github.com/angular/angular.js/commit/aa2133ad818d2e5c27cbd3933061797096356c8a).
|
||||
|
||||
|
||||
## URLs are now sanitized against a whitelist
|
||||
### URLs are now sanitized against a whitelist
|
||||
|
||||
A whitelist configured via `$compileProvider` can be used to configure what URLs are considered safe.
|
||||
By default all common protocol prefixes are whitelisted including `data:` URIs with mime types `image/*`.
|
||||
@@ -1367,7 +1668,7 @@ See [1adf29af](https://github.com/angular/angular.js/commit/1adf29af13890d612868
|
||||
[3e39ac7e](https://github.com/angular/angular.js/commit/3e39ac7e1b10d4812a44dad2f959a93361cd823b).
|
||||
|
||||
|
||||
## Isolate scope only exposed to directives with `scope` property
|
||||
### Isolate scope only exposed to directives with `scope` property
|
||||
|
||||
If you declare a scope option on a directive, that directive will have an
|
||||
[isolate scope](https://github.com/angular/angular.js/wiki/Understanding-Scopes). In Angular 1.0, if a
|
||||
@@ -1440,7 +1741,7 @@ See [909cabd3](https://github.com/angular/angular.js/commit/909cabd36d779598763c
|
||||
[#2500](https://github.com/angular/angular.js/issues/2500).
|
||||
|
||||
|
||||
## Change to interpolation priority
|
||||
### Change to interpolation priority
|
||||
|
||||
Previously, the interpolation priority was `-100` in 1.2.0-rc.2, and `100` before 1.2.0-rc.2.
|
||||
Before this change the binding was setup in the post-linking phase.
|
||||
@@ -1453,7 +1754,7 @@ See [79223eae](https://github.com/angular/angular.js/commit/79223eae502283889334
|
||||
[#4528](https://github.com/angular/angular.js/issues/4528), and
|
||||
[#4649](https://github.com/angular/angular.js/issues/4649)
|
||||
|
||||
## Underscore-prefixed/suffixed properties are non-bindable
|
||||
### Underscore-prefixed/suffixed properties are non-bindable
|
||||
|
||||
<div class="alert alert-info">
|
||||
<p>**Reverted**: This breaking change has been reverted in 1.2.1, and so can be ignored if you're using **version 1.2.1 or higher**</p>
|
||||
@@ -1492,7 +1793,7 @@ are actually needed by the expressions.
|
||||
See [3d6a89e8](https://github.com/angular/angular.js/commit/3d6a89e8888b14ae5cb5640464e12b7811853c7e).
|
||||
|
||||
|
||||
## You cannot bind to select[multiple]
|
||||
### You cannot bind to select[multiple]
|
||||
|
||||
Switching between `select[single]` and `select[multiple]` has always been odd due to browser quirks.
|
||||
This feature never worked with two-way data-binding so it's not expected that anyone is using it.
|
||||
@@ -1502,7 +1803,7 @@ If you are interested in properly adding this feature, please submit a pull requ
|
||||
See [d87fa004](https://github.com/angular/angular.js/commit/d87fa0042375b025b98c40bff05e5f42c00af114).
|
||||
|
||||
|
||||
## Uncommon region-specific local files were removed from i18n
|
||||
### Uncommon region-specific local files were removed from i18n
|
||||
|
||||
AngularJS uses the Google Closure library's locale files. The following locales were removed from
|
||||
Closure, so Angular is not able to continue to support them:
|
||||
@@ -1518,7 +1819,7 @@ load and use your copy of the locale file provided that you maintain it yourself
|
||||
|
||||
See [6382e21f](https://github.com/angular/angular.js/commit/6382e21fb28541a2484ac1a241d41cf9fbbe9d2c).
|
||||
|
||||
## Services can now return functions
|
||||
### Services can now return functions
|
||||
|
||||
Previously, the service constructor only returned objects regardless of whether a function was returned.
|
||||
|
||||
|
||||
@@ -75,9 +75,8 @@ that you break your application to multiple modules like this:
|
||||
* And an application level module which depends on the above modules and contains any
|
||||
initialization code.
|
||||
|
||||
We've also
|
||||
[written a document](http://blog.angularjs.org/2014/02/an-angularjs-style-guide-and-best.html)
|
||||
on how we organize large apps at Google.
|
||||
You can find a community
|
||||
[style guide](https://github.com/johnpapa/angular-styleguide) to help yourself when application grows.
|
||||
|
||||
The above is a suggestion. Tailor it to your needs.
|
||||
|
||||
@@ -140,7 +139,7 @@ The above is a suggestion. Tailor it to your needs.
|
||||
# Module Loading & Dependencies
|
||||
|
||||
A module is a collection of configuration and run blocks which get applied to the application
|
||||
during the bootstrap process. In its simplest form the module consist of a collection of two kinds
|
||||
during the bootstrap process. In its simplest form the module consists of a collection of two kinds
|
||||
of blocks:
|
||||
|
||||
1. **Configuration blocks** - get executed during the provider registrations and configuration
|
||||
|
||||
@@ -44,7 +44,7 @@ and {@link angular.reloadWithDebugInfo `angular.reloadWithDebugInfo`}.
|
||||
|
||||
## Strict DI Mode
|
||||
|
||||
Using strict di mode in your production application will throw errors when a injectable
|
||||
Using strict di mode in your production application will throw errors when an injectable
|
||||
function is not
|
||||
{@link di#dependency-annotation annotated explicitly}. Strict di mode is intended to help
|
||||
you make sure that your code will work when minified. However, it also will force you to
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
|
||||
# What are Scopes?
|
||||
|
||||
{@link ng.$rootScope.Scope scope} is an object that refers to the application
|
||||
{@link ng.$rootScope.Scope Scope} is an object that refers to the application
|
||||
model. It is an execution context for {@link expression expressions}. Scopes are
|
||||
arranged in hierarchical structure which mimic the DOM structure of the application. Scopes can
|
||||
watch {@link guide/expression expressions} and propagate events.
|
||||
@@ -391,7 +391,7 @@ implementing custom event callbacks, or when working with third-party library ca
|
||||
5. The {@link ng.$rootScope.Scope#$watch $watch} list is a set of expressions
|
||||
which may have changed since last iteration. If a change is detected then the `$watch`
|
||||
function is called which typically updates the DOM with the new value.
|
||||
6. Once the Angular {@link ng.$rootScope.Scope#$digest $digest} loop finishes
|
||||
6. Once the Angular {@link ng.$rootScope.Scope#$digest $digest} loop finishes,
|
||||
the execution leaves the Angular and JavaScript context. This is followed by the browser
|
||||
re-rendering the DOM to reflect any changes.
|
||||
|
||||
@@ -419,4 +419,4 @@ user enters text into the text field.
|
||||
which in turn updates the DOM.
|
||||
6. Angular exits the execution context, which in turn exits the `keydown` event and with it
|
||||
the JavaScript execution context.
|
||||
7. The browser re-renders the view with update text.
|
||||
7. The browser re-renders the view with the updated text.
|
||||
|
||||
@@ -39,7 +39,7 @@ In general, we recommend against this because it can create unintended XSS vecto
|
||||
|
||||
However, it's ok to mix server-side templating in the bootstrap template (`index.html`) as long
|
||||
as user input cannot be used on the server to output html that would then be processed by Angular
|
||||
in a way that would cause allow for arbitrary code execution.
|
||||
in a way that would allow for arbitrary code execution.
|
||||
|
||||
For instance, you can use server-side templating to dynamically generate CSS, URLs, etc, but not
|
||||
for generating templates that are bootstrapped/compiled by Angular.
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
JavaScript is a dynamically typed language which comes with great power of expression, but it also
|
||||
comes with almost no help from the compiler. For this reason we feel very strongly that any code
|
||||
written in JavaScript needs to come with a strong set of tests. We have built many features into
|
||||
Angular which makes testing your Angular applications easy. So there is no excuse for not testing.
|
||||
Angular which make testing your Angular applications easy. With Angular, there is no excuse for not testing.
|
||||
|
||||
## Separation of Concerns
|
||||
|
||||
@@ -20,13 +20,13 @@ related pieces such as the DOM elements, or making any XHR calls to fetch the da
|
||||
|
||||
While this may seem obvious it can be very difficult to call an individual function on a
|
||||
typical project. The reason is that the developers often mix concerns resulting in a
|
||||
piece of code which does everything. It makes an XHR request, it sorts the response data and then it
|
||||
piece of code which does everything. It makes an XHR request, it sorts the response data, and then it
|
||||
manipulates the DOM.
|
||||
|
||||
With Angular we try to make it easy for you to do the right thing, and so we
|
||||
provide dependency injection for your XHR requests, which can be mocked, and we provide abstractions which
|
||||
allow you to test your model without having to resort to manipulating the DOM. The test can then
|
||||
assert that the data has been sorted without having to create or look at the state of the DOM or
|
||||
With Angular, we try to make it easy for you to do the right thing. For your XHR requests, we
|
||||
provide dependency injection, so your requests can be simulated. For the DOM, we abstract it, so you can
|
||||
test your model without having to manipulate the DOM directly. Your tests can then
|
||||
assert that the data has been sorted without having to create or look at the state of the DOM or to
|
||||
wait for any XHR requests to return data. The individual sort function can be tested in isolation.
|
||||
|
||||
## With great power comes great responsibility
|
||||
@@ -261,8 +261,10 @@ myModule.filter('length', function() {
|
||||
|
||||
describe('length filter', function() {
|
||||
|
||||
var $filter;
|
||||
|
||||
beforeEach(inject(function(_$filter_){
|
||||
$filter= _$filter_;
|
||||
$filter = _$filter_;
|
||||
}));
|
||||
|
||||
it('returns 0 when given null', function() {
|
||||
@@ -357,7 +359,7 @@ element, to which it can then insert the transcluded content into its template.
|
||||
|
||||
Before compilation:
|
||||
```html
|
||||
<div translude-directive>
|
||||
<div transclude-directive>
|
||||
Some transcluded content
|
||||
</div>
|
||||
```
|
||||
|
||||
@@ -15,14 +15,14 @@ development.
|
||||
production.
|
||||
|
||||
To point your code to an angular script on the Google CDN server, use the following template. This
|
||||
example points to the minified version 1.3.14:
|
||||
example points to the minified version 1.4.5:
|
||||
|
||||
```
|
||||
<!doctype html>
|
||||
<html ng-app>
|
||||
<head>
|
||||
<title>My Angular App</title>
|
||||
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.14/angular.min.js"></script>
|
||||
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.5/angular.min.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
</body>
|
||||
@@ -46,7 +46,7 @@ Download the version you want and have fun.
|
||||
Each directory under <http://code.angularjs.org/> includes the following set of files:
|
||||
|
||||
* __`angular.js`__ — This file is non-obfuscated, non-minified, and human-readable by
|
||||
opening it it any editor or browser. In order to get better error messages during development, you
|
||||
opening it in any editor or browser. In order to get better error messages during development, you
|
||||
should always use this non-minified angular script.
|
||||
|
||||
* __`angular.min.js`__ — This is a minified and obfuscated version of
|
||||
|
||||
@@ -86,9 +86,15 @@ Yes. See instructions in {@link downloading}.
|
||||
|
||||
### What browsers does Angular work with?
|
||||
|
||||
We run our extensive test suite against the following browsers: Safari, Chrome, Firefox, Opera 15,
|
||||
IE9 and mobile browsers (Android, Chrome Mobile, iOS Safari). See {@link guide/ie Internet
|
||||
Explorer Compatibility} for more details on supporting legacy IE browsers.
|
||||
We run our extensive test suite against the following browsers: the latest versions of Chrome,
|
||||
Firefox, Safari, and Safari for iOs, as well as Internet Explorer versions 9-11. See {@link guide/ie
|
||||
Internet Explorer Compatibility} for more details on supporting legacy IE browsers.
|
||||
|
||||
If a browser is untested, it doesn't mean it won't work; for example, older Android (2.3.x)
|
||||
is supported in the sense that we avoid the dot notation for reserved words as property names,
|
||||
but we don't actively test changes against it. You can also expect browsers to work that share
|
||||
a large part of their codebase with a browser we test, such as Opera > version 12
|
||||
(uses the Blink engine), or the various Firefox derivatives.
|
||||
|
||||
|
||||
### What's Angular's performance like?
|
||||
@@ -194,7 +200,7 @@ Conditionally showing and hiding things using jQuery is a common pattern in othe
|
||||
`ng-show` (and `ng-hide`) conditionally show and hide elements based on boolean expressions.
|
||||
Describe the conditions for showing and hiding an element in terms of `$scope` variables:
|
||||
|
||||
<div ng-show="!loggedIn">Click <a href="#/login">here</a> to log in</div>
|
||||
<div ng-show="!loggedIn"><a href="#/login">Click here to log in</a></div>
|
||||
|
||||
Note also the counterpart `ng-hide` and similar `ng-disabled`.
|
||||
Note especially the powerful `ng-switch` that should be used instead of several mutually exclusive `ng-show`s.
|
||||
|
||||
@@ -61,7 +61,7 @@ a few git commands.
|
||||
|
||||
### Install Git
|
||||
|
||||
You can download and install Git from http://git-scm.com/download. Once installed you should have
|
||||
You can download and install Git from http://git-scm.com/download. Once installed, you should have
|
||||
access to the `git` command line tool. The main commands that you will need to use are:
|
||||
|
||||
- `git clone ...` : clone a remote repository onto your local machine
|
||||
@@ -123,13 +123,14 @@ npm --version
|
||||
</a>.
|
||||
</div>
|
||||
|
||||
Once you have Node.js installed on your machine you can download the tool dependencies by running:
|
||||
Once you have Node.js installed on your machine, you can download the tool dependencies by running:
|
||||
|
||||
```
|
||||
npm install
|
||||
```
|
||||
|
||||
This command will download the following tools, into the `node_modules` directory:
|
||||
This command reads angular-phonecat's `package.json` file and downloads the following tools
|
||||
into the `node_modules` directory:
|
||||
|
||||
- [Bower][bower] - client-side code package manager
|
||||
- [Http-Server][http-server] - simple local static web server
|
||||
@@ -197,8 +198,8 @@ http://localhost:8000/app/index.html
|
||||
```
|
||||
|
||||
<div class="alert alert-info">
|
||||
To serve the web app on a different ip address or port, edit the "start" script within package.json.
|
||||
You can `-a` to set the address and `-p` to set the port.
|
||||
To serve the web app on a different IP address or port, edit the "start" script within package.json.
|
||||
You can use `-a` to set the address and `-p` to set the port.
|
||||
</div>
|
||||
|
||||
### Running Unit Tests
|
||||
@@ -245,6 +246,15 @@ npm run update-webdriver
|
||||
|
||||
*(You should only need to do this once.)*
|
||||
|
||||
You will need to have Java present on your dev machine to allow the Selenium standalone to be started.
|
||||
Check if you already have java installed by opening a terminal/command line window and typing
|
||||
'''
|
||||
java -version
|
||||
'''
|
||||
If java is already installed and exists in the PATH then you will be shown the version installed,
|
||||
if, however you receive a message that "java is not recognized as an internal command or external
|
||||
command" you will need to install [java].
|
||||
|
||||
Since Protractor works by interacting with a running application, we need to start our web server:
|
||||
|
||||
```
|
||||
@@ -270,6 +280,7 @@ It is good to run the end to end tests whenever you make changes to the HTML vie
|
||||
that the application as a whole is executing correctly. It is very common to run End to End tests
|
||||
before pushing a new commit of changes to a remote repository.
|
||||
|
||||
Now that you have set up your local machine, let's get started with the tutorial: {@link step_00 Step 0 - Bootstrapping}
|
||||
|
||||
[git]: http://git-scm.com/
|
||||
[node]: http://nodejs.org/
|
||||
@@ -278,3 +289,4 @@ before pushing a new commit of changes to a remote repository.
|
||||
[bower]: http://bower.io/
|
||||
[http-server]: https://github.com/nodeapps/http-server
|
||||
[karma]: https://github.com/karma-runner/karma
|
||||
[java]: https://www.java.com/en/download/help/download_options.xml
|
||||
|
||||
@@ -6,12 +6,14 @@
|
||||
<ul doc-tutorial-nav="0"></ul>
|
||||
|
||||
|
||||
You are now ready to build the AngularJS phonecat app. In this step, you will become familiar
|
||||
with the most important source code files, learn how to start the development servers bundled with
|
||||
In this step of the tutorial, you will become familiar with the most important source code files of
|
||||
the AngularJS phonecat app. You will also learn how to start the development servers bundled with
|
||||
angular-seed, and run the application in the browser.
|
||||
|
||||
Before you continue, make sure you have set up your development environment and installed all necessary
|
||||
dependencies, as described in {@link index#get-started Get Started}.
|
||||
|
||||
In `angular-phonecat` directory, run this command:
|
||||
In the `angular-phonecat` directory, run this command:
|
||||
|
||||
```
|
||||
git checkout -f step-0
|
||||
@@ -31,7 +33,7 @@ npm install
|
||||
|
||||
To see the app running in a browser, open a *separate* terminal/command line tab or window, then
|
||||
run `npm start` to start the web server. Now, open a browser window for the app and navigate to
|
||||
<a href="http://localhost:8000/app/" target="_blank">`http://localhost:8000/app/`</a>
|
||||
<a href="http://localhost:8000/app/" target="_blank" title="Open app on localhost">`http://localhost:8000/app/`</a>
|
||||
|
||||
Note that if you already ran the master branch app prior to checking out step-0, you may see the cached
|
||||
master version of the app in your browser window at this point. Just hit refresh to re-load the page.
|
||||
@@ -91,22 +93,22 @@ being the element on which the `ngApp` directive was defined.
|
||||
|
||||
Nothing here {{'yet' + '!'}}
|
||||
|
||||
This line demonstrates two core features of Angular's templating capabilities:
|
||||
This line demonstrates two core features of Angular's templating capabilities:
|
||||
|
||||
* a binding, denoted by double-curlies `{{ }}`
|
||||
* a simple expression `'yet' + '!'` used in this binding.
|
||||
* a binding, denoted by double-curlies `{{ }}`
|
||||
* a simple expression `'yet' + '!'` used in this binding.
|
||||
|
||||
The binding tells Angular that it should evaluate an expression and insert the result into the
|
||||
DOM in place of the binding. Rather than a one-time insert, as we'll see in the next steps, a
|
||||
binding will result in efficient continuous updates whenever the result of the expression
|
||||
evaluation changes.
|
||||
The binding tells Angular that it should evaluate an expression and insert the result into the
|
||||
DOM in place of the binding. Rather than a one-time insert, as we'll see in the next steps, a
|
||||
binding will result in efficient continuous updates whenever the result of the expression
|
||||
evaluation changes.
|
||||
|
||||
{@link guide/expression Angular expression} is a JavaScript-like code snippet that is
|
||||
evaluated by Angular in the context of the current model scope, rather than within the scope of
|
||||
the global context (`window`).
|
||||
{@link guide/expression Angular expression} is a JavaScript-like code snippet that is
|
||||
evaluated by Angular in the context of the current model scope, rather than within the scope of
|
||||
the global context (`window`).
|
||||
|
||||
As expected, once this template is processed by Angular, the html page contains the text:
|
||||
"Nothing here yet!".
|
||||
As expected, once this template is processed by Angular, the html page contains the text:
|
||||
"Nothing here yet!".
|
||||
|
||||
## Bootstrapping AngularJS apps
|
||||
|
||||
|
||||
@@ -61,7 +61,7 @@ by the value of the expressions.
|
||||
We have added a new directive, called `ng-controller`, which attaches a `PhoneListCtrl`
|
||||
__controller__ to the <body> tag. At this point:
|
||||
|
||||
* The expressions in curly braces (`{{phone.name}}` and `{{phone.snippet}}` denote
|
||||
* The expressions in curly braces (`{{phone.name}}` and `{{phone.snippet}}`) denote
|
||||
bindings, which are referring to our application model, which is set up in our `PhoneListCtrl`
|
||||
controller.
|
||||
|
||||
@@ -132,6 +132,8 @@ The "Angular way" of separating controller from the view, makes it easy to test
|
||||
developed. If our controller is available on the global namespace then we could simply instantiate it
|
||||
with a mock `scope` object:
|
||||
|
||||
__`test/e2e/scenarios.js`:__
|
||||
|
||||
```js
|
||||
describe('PhoneListCtrl', function(){
|
||||
|
||||
@@ -195,8 +197,19 @@ to ensure that Karma and its necessary plugins are installed. You can do this by
|
||||
|
||||
To run the tests, and then watch the files for changes: `npm test`.
|
||||
|
||||
* Karma will start a new instance of Chrome browser automatically. Just ignore it and let it run in
|
||||
the background. Karma will use this browser for test execution.
|
||||
* Karma will start new instances of Chrome and Firefox browsers automatically. Just ignore them and
|
||||
let them run in the background. Karma will use these browsers for test execution.
|
||||
* If you only have one of the browsers installed on your machine (either Chrome or Firefox), make
|
||||
sure to update the karma configuration file before running the test. Locate the configuration file
|
||||
in `test/karma.conf.js`, then update the `browsers` property.
|
||||
|
||||
E.g. if you only have Chrome installed:
|
||||
<pre>
|
||||
...
|
||||
browsers: ['Chrome'],
|
||||
...
|
||||
</pre>
|
||||
|
||||
* You should see the following or similar output in the terminal:
|
||||
|
||||
<pre>
|
||||
@@ -250,7 +263,7 @@ browser is limited, which results in your karma tests running extremely slow.
|
||||
<tr><th>row number</th></tr>
|
||||
<tr ng-repeat="i in [0, 1, 2, 3, 4, 5, 6, 7]"><td>{{i+1}}</td></tr>
|
||||
</table>
|
||||
|
||||
|
||||
Extra points: try and make an 8x8 table using an additional `ng-repeat`.
|
||||
|
||||
* Make the unit test fail by changing `expect(scope.phones.length).toBe(3)` to instead use `toBe(4)`.
|
||||
|
||||
@@ -65,7 +65,7 @@ phonecatApp.controller('PhoneListCtrl', function ($scope, $http) {
|
||||
`$http` makes an HTTP GET request to our web server, asking for `phones/phones.json` (the url is
|
||||
relative to our `index.html` file). The server responds by providing the data in the json file.
|
||||
(The response might just as well have been dynamically generated by a backend server. To the
|
||||
browser and our app they both look the same. For the sake of simplicity we used a json file in this
|
||||
browser and our app, they both look the same. For the sake of simplicity, we used a json file in this
|
||||
tutorial.)
|
||||
|
||||
The `$http` service returns a {@link ng.$q promise object} with a `success`
|
||||
@@ -114,7 +114,7 @@ as strings, which will not get minified. There are two ways to provide these inj
|
||||
|
||||
* Create a `$inject` property on the controller function which holds an array of strings.
|
||||
Each string in the array is the name of the service to inject for the corresponding parameter.
|
||||
In our example we would write:
|
||||
In our example, we would write:
|
||||
|
||||
```js
|
||||
function PhoneListCtrl($scope, $http) {...}
|
||||
|
||||
@@ -43,7 +43,7 @@ __`app/index.html`:__
|
||||
...
|
||||
<ul class="phones">
|
||||
<li ng-repeat="phone in phones | filter:query | orderBy:orderProp" class="thumbnail">
|
||||
<a href="#/phones/{{phone.id}}" class="thumb"><img ng-src="{{phone.imageUrl}}"></a>
|
||||
<a href="#/phones/{{phone.id}}" class="thumb"><img ng-src="{{phone.imageUrl}}" alt="{{phone.name}}"></a>
|
||||
<a href="#/phones/{{phone.id}}">{{phone.name}}</a>
|
||||
<p>{{phone.snippet}}</p>
|
||||
</li>
|
||||
@@ -59,8 +59,8 @@ the element attribute.
|
||||
We also added phone images next to each record using an image tag with the {@link
|
||||
ng.directive:ngSrc ngSrc} directive. That directive prevents the
|
||||
browser from treating the Angular `{{ expression }}` markup literally, and initiating a request to
|
||||
invalid URL `http://localhost:8000/app/{{phone.imageUrl}}`, which it would have done if we had only
|
||||
specified an attribute binding in a regular `src` attribute (`<img src="{{phone.imageUrl}}">`).
|
||||
an invalid URL `http://localhost:8000/app/{{phone.imageUrl}}`, which it would have done if we had
|
||||
only specified an attribute binding in a regular `src` attribute (`<img src="{{phone.imageUrl}}">`).
|
||||
Using the `ngSrc` directive prevents the browser from making an http request to an invalid location.
|
||||
|
||||
|
||||
@@ -75,7 +75,7 @@ __`test/e2e/scenarios.js`__:
|
||||
query.sendKeys('nexus');
|
||||
element.all(by.css('.phones li a')).first().click();
|
||||
browser.getLocationAbsUrl().then(function(url) {
|
||||
expect(url.split('#')[1]).toBe('/phones/nexus-s');
|
||||
expect(url).toBe('/phones/nexus-s');
|
||||
});
|
||||
});
|
||||
...
|
||||
|
||||
@@ -33,17 +33,17 @@ We are using [Bower][bower] to install client-side dependencies. This step upda
|
||||
"license": "MIT",
|
||||
"private": true,
|
||||
"dependencies": {
|
||||
"angular": "~1.3.0",
|
||||
"angular-mocks": "~1.3.0",
|
||||
"jquery": "2.1.1",
|
||||
"angular": "1.4.x",
|
||||
"angular-mocks": "1.4.x",
|
||||
"jquery": "~2.1.1",
|
||||
"bootstrap": "~3.1.1",
|
||||
"angular-route": "~1.3.0"
|
||||
"angular-route": "1.4.x"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
The new dependency `"angular-route": "~1.3.0"` tells bower to install a version of the
|
||||
angular-route component that is compatible with version 1.3.x. We must tell bower to download
|
||||
The new dependency `"angular-route": "1.4.x"` tells bower to install a version of the
|
||||
angular-route component that is compatible with version 1.4.x. We must tell bower to download
|
||||
and install this dependency.
|
||||
|
||||
If you have bower installed globally, then you can run `bower install` but for this project, we have
|
||||
@@ -53,6 +53,18 @@ preconfigured npm to run bower install for us:
|
||||
npm install
|
||||
```
|
||||
|
||||
<div class="alert alert-warning">
|
||||
**Warning:** If a new version of Angular has been released since you last ran `npm install`, then you may have a
|
||||
problem with the `bower install` due to a conflict between the versions of angular.js that need to
|
||||
be installed. If you get this then simply delete your `app/bower_components` folder before running
|
||||
`npm install`.
|
||||
</div>
|
||||
|
||||
<div class="alert alert-info">
|
||||
**Note:** If you have bower installed globally then you can run `bower install` but for this project we have
|
||||
preconfigured `npm install` to run bower for us.
|
||||
</div>
|
||||
|
||||
|
||||
## Multiple Views, Routing and Layout Template
|
||||
|
||||
@@ -313,7 +325,7 @@ to various URLs and verify that the correct view was rendered.
|
||||
it('should redirect index.html to index.html#/phones', function() {
|
||||
browser.get('app/index.html');
|
||||
browser.getLocationAbsUrl().then(function(url) {
|
||||
expect(url.split('#')[1]).toBe('/phones');
|
||||
expect(url).toEqual('/phones');
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -12,8 +12,8 @@ phone in the phone list.
|
||||
* When you click on a phone on the list, the phone details page with phone-specific information
|
||||
is displayed.
|
||||
|
||||
To implement the phone details view we used {@link ng.$http $http} to fetch our data, and we
|
||||
fleshed out the `phone-detail.html` view template.
|
||||
To implement the phone details view we are going to use {@link ng.$http $http} to fetch our data,
|
||||
and then flesh out the `phone-detail.html` view template.
|
||||
|
||||
<div doc-tutorial-reset="8"></div>
|
||||
|
||||
|
||||
@@ -32,17 +32,18 @@ We are using [Bower][bower] to install client side dependencies. This step upda
|
||||
"license": "MIT",
|
||||
"private": true,
|
||||
"dependencies": {
|
||||
"angular": "~1.3.0",
|
||||
"angular-mocks": "~1.3.0",
|
||||
"angular": "1.4.x",
|
||||
"angular-mocks": "1.4.x",
|
||||
"jquery": "~2.1.1",
|
||||
"bootstrap": "~3.1.1",
|
||||
"angular-route": "~1.3.0",
|
||||
"angular-resource": "~1.3.0"
|
||||
"angular-route": "1.4.x",
|
||||
"angular-resource": "1.4.x"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
The new dependency `"angular-resource": "~1.3.0"` tells bower to install a version of the
|
||||
angular-resource component that is compatible with version 1.3.x. We must ask bower to download
|
||||
The new dependency `"angular-resource": "1.4.x"` tells bower to install a version of the
|
||||
angular-resource component that is compatible with version 1.4.x. We must ask bower to download
|
||||
and install this dependency. We can do this by running:
|
||||
|
||||
```
|
||||
|
||||
@@ -36,20 +36,20 @@ We are using [Bower][bower] to install client side dependencies. This step upda
|
||||
"license": "MIT",
|
||||
"private": true,
|
||||
"dependencies": {
|
||||
"angular": "~1.3.0",
|
||||
"angular-mocks": "~1.3.0",
|
||||
"bootstrap": "~3.1.1",
|
||||
"angular-route": "~1.3.0",
|
||||
"angular-resource": "~1.3.0",
|
||||
"angular": "1.4.x",
|
||||
"angular-mocks": "1.4.x",
|
||||
"jquery": "~2.1.1",
|
||||
"angular-animate": "~1.3.0"
|
||||
"bootstrap": "~3.1.1",
|
||||
"angular-route": "1.4.x",
|
||||
"angular-resource": "1.4.x",
|
||||
"angular-animate": "1.4.x"
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
* `"angular-animate": "~1.3.0"` tells bower to install a version of the
|
||||
angular-animate component that is compatible with version 1.3.x.
|
||||
* `"jquery": "2.1.1"` tells bower to install the 2.1.1 version of jQuery. Note that this is not an
|
||||
* `"angular-animate": "1.4.x"` tells bower to install a version of the
|
||||
angular-animate component that is compatible with version 1.4.x.
|
||||
* `"jquery": "~2.1.1"` tells bower to install the 2.1.1 version of jQuery. Note that this is not an
|
||||
Angular library, it is the standard jQuery library. We can use bower to install a wide range of 3rd
|
||||
party libraries.
|
||||
|
||||
@@ -111,7 +111,7 @@ __`app/index.html`.__
|
||||
```
|
||||
|
||||
<div class="alert alert-error">
|
||||
**Important:** Be sure to use jQuery version 2.1 or newer when using Angular 1.3; jQuery 1.x is
|
||||
**Important:** Be sure to use jQuery version 2.1 or newer when using Angular 1.4; jQuery 1.x is
|
||||
not officially supported.
|
||||
Be sure to load jQuery before all AngularJS scripts, otherwise AngularJS won't detect jQuery and
|
||||
animations will not work as expected.
|
||||
@@ -239,9 +239,9 @@ The name of the starting class is the name of the event that is fired (like `ent
|
||||
The active class name is the same as the starting class's but with an `-active` suffix.
|
||||
This two-class CSS naming convention allows the developer to craft an animation, beginning to end.
|
||||
|
||||
In our example above, elements expand from a height of **0** to **120 pixels** when items are added or moved,
|
||||
around and collapsing the items before removing them from the list.
|
||||
There's also a nice fade-in and fade-out effect that also occurs at the same time. All of this is handled
|
||||
In our example above, elements are expanded from a height of **0** to **120 pixels** when they're added to the
|
||||
list and are collapsed back down to **0 pixels** before being removed from the list.
|
||||
There's also a nice fade-in and fade-out effect that occurs at the same time. All of this is handled
|
||||
by the CSS transition declarations at the top of the example code above.
|
||||
|
||||
Although most modern browsers have good support for [CSS transitions](http://caniuse.com/#feat=css-transitions)
|
||||
@@ -357,10 +357,10 @@ For more on CSS animations, see the
|
||||
## Animating `ngClass` with JavaScript
|
||||
|
||||
Let's add another animation to our application. Switching to our `phone-detail.html` page,
|
||||
we see that we have a nice thumbnail swapper. By clicking on the thumbnails listed on the page,
|
||||
we see that we have a nice thumbnail swapper. By hovering over the thumbnails listed on the page,
|
||||
the profile phone image changes. But how can we change this around to add animations?
|
||||
|
||||
Let's think about it first. Basically, when you click on a thumbnail image, you're changing the
|
||||
Let's think about it first. Basically, when you hover over a thumbnail image, you're changing the
|
||||
state of the profile image to reflect the newly selected thumbnail image.
|
||||
The best way to specify state changes within HTML is to use classes.
|
||||
Much like before, how we used a CSS class to specify an animation, this time the animation will
|
||||
@@ -369,7 +369,7 @@ occur whenever the CSS class itself changes.
|
||||
Whenever a new phone thumbnail is selected, the state changes and the `.active` CSS class is added
|
||||
to the matching profile image and the animation plays.
|
||||
|
||||
Let's get started and tweak our HTML code on the `phone-detail.html` page first. Notice that we
|
||||
Let's get started and tweak our HTML code on the `phone-detail.html` page first. Notice that we
|
||||
have changed the way we display our large image:
|
||||
|
||||
__`app/partials/phone-detail.html`.__
|
||||
|
||||
+3
-2
@@ -21,6 +21,7 @@ var outputFolder = '../build/docs';
|
||||
var bowerFolder = 'bower_components';
|
||||
|
||||
var src = 'app/src/**/*.js';
|
||||
var ignoredFiles = '!src/angular.bind.js';
|
||||
var assets = 'app/assets/**/*';
|
||||
|
||||
|
||||
@@ -50,7 +51,7 @@ gulp.task('build-app', function() {
|
||||
var minFile = 'docs.min.js';
|
||||
var folder = outputFolder + '/js/';
|
||||
|
||||
return gulp.src(src)
|
||||
return gulp.src([src, ignoredFiles])
|
||||
.pipe(sourcemaps.init())
|
||||
.pipe(concat(file))
|
||||
.pipe(gulp.dest(folder))
|
||||
@@ -107,5 +108,5 @@ gulp.task('jshint', ['doc-gen'], function() {
|
||||
gulp.task('default', ['assets', 'doc-gen', 'build-app', 'jshint']);
|
||||
|
||||
gulp.task('watch', function() {
|
||||
gulp.watch([src, assets], ['assets', 'build-app']);
|
||||
gulp.watch([src, ignoredFiles, assets], ['assets', 'build-app']);
|
||||
});
|
||||
|
||||
@@ -173,7 +173,7 @@ function request(method, url, options, response) {
|
||||
res.on('error', function (e) { console.log(e); });
|
||||
break;
|
||||
case 401:
|
||||
console.log('Eror: Login credentials expired! Please login.');
|
||||
console.log('Error: Login credentials expired! Please login.');
|
||||
break;
|
||||
default:
|
||||
data = [];
|
||||
|
||||
@@ -303,8 +303,8 @@ goog.i18n.currency.CurrencyInfo = {
|
||||
'KRW': [0, '\u20A9', 'KR₩'],
|
||||
'LKR': [2, 'Rs', 'SLRs'],
|
||||
'LTL': [2, 'Lt', 'Lt'],
|
||||
'LVL': [2, 'Ls', 'Ls'],
|
||||
'MNT': [0, '\u20AE', 'MN₮'],
|
||||
'MVR': [2, 'Rf', 'MVR'],
|
||||
'MXN': [2, '$', 'Mex$'],
|
||||
'MYR': [2, 'RM', 'RM'],
|
||||
'NOK': [50, 'kr', 'NOkr'],
|
||||
@@ -339,6 +339,7 @@ goog.i18n.currency.CurrencyInfo = {
|
||||
goog.i18n.currency.CurrencyInfoTier2 = {
|
||||
'AFN': [48, 'Af.', 'AFN'],
|
||||
'AMD': [0, 'Dram', 'dram'],
|
||||
'ANG': [2, 'NAf.', 'ANG'],
|
||||
'AOA': [2, 'Kz', 'Kz'],
|
||||
'ARS': [2, '$', 'AR$'],
|
||||
'AWG': [2, 'Afl.', 'Afl.'],
|
||||
@@ -414,6 +415,7 @@ goog.i18n.currency.CurrencyInfoTier2 = {
|
||||
'SLL': [0, 'SLL', 'SLL'],
|
||||
'SOS': [0, 'SOS', 'SOS'],
|
||||
'SRD': [2, '$', 'SR$'],
|
||||
'SSP': [2, '£', 'SSP'],
|
||||
'STD': [0, 'Db', 'Db'],
|
||||
'SYP': [0, '£', 'SY£'],
|
||||
'SZL': [2, 'SZL', 'SZL'],
|
||||
@@ -430,5 +432,6 @@ goog.i18n.currency.CurrencyInfoTier2 = {
|
||||
'XCD': [2, '$', 'EC$'],
|
||||
'XOF': [0, 'CFA', 'CFA'],
|
||||
'XPF': [0, 'FCFP', 'FCFP'],
|
||||
'ZMK': [0, 'ZMK', 'ZMK']
|
||||
'ZMW': [0, 'ZMW', 'ZMW'],
|
||||
'ZWD': [0, '$', 'Z$']
|
||||
};
|
||||
|
||||
+305
-54
@@ -17,7 +17,7 @@
|
||||
*
|
||||
* This file is autogenerated by script. See
|
||||
* http://go/generate_datetime_constants.py using --for_closure
|
||||
* File generated from CLDR ver. 26
|
||||
* File generated from CLDR ver. 27.0.1
|
||||
*
|
||||
* To reduce the file size (which may cause issues in some JS
|
||||
* developing environments), this file will only contain locales
|
||||
@@ -36,9 +36,11 @@ goog.provide('goog.i18n.DateTimeSymbols_af');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_am');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_ar');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_az');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_be');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_bg');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_bn');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_br');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_bs');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_ca');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_chr');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_cs');
|
||||
@@ -50,6 +52,7 @@ goog.provide('goog.i18n.DateTimeSymbols_de_CH');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_el');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_en');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_en_AU');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_en_CA');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_en_GB');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_en_IE');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_en_IN');
|
||||
@@ -60,6 +63,8 @@ goog.provide('goog.i18n.DateTimeSymbols_en_ZA');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_es');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_es_419');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_es_ES');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_es_MX');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_es_US');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_et');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_eu');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_fa');
|
||||
@@ -118,6 +123,7 @@ goog.provide('goog.i18n.DateTimeSymbols_sk');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_sl');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_sq');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_sr');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_sr_Latn');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_sv');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_sw');
|
||||
goog.provide('goog.i18n.DateTimeSymbols_ta');
|
||||
@@ -343,6 +349,52 @@ goog.i18n.DateTimeSymbols_az = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale be.
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_be = {
|
||||
ERAS: ['да н.э.', 'н.э.'],
|
||||
ERANAMES: ['да н.э.', 'н.э.'],
|
||||
NARROWMONTHS: ['с', 'л', 'с', 'к', 'м', 'ч', 'л', 'ж', 'в', 'к',
|
||||
'л', 'с'],
|
||||
STANDALONENARROWMONTHS: ['с', 'л', 'с', 'к', 'м', 'ч', 'л', 'ж', 'в',
|
||||
'к', 'л', 'с'],
|
||||
MONTHS: ['студзеня', 'лютага', 'сакавіка',
|
||||
'красавіка', 'мая', 'чэрвеня', 'ліпеня',
|
||||
'жніўня', 'верасня', 'кастрычніка',
|
||||
'лістапада', 'снежня'],
|
||||
STANDALONEMONTHS: ['студзень', 'люты', 'сакавік',
|
||||
'красавік', 'май', 'чэрвень', 'ліпень',
|
||||
'жнівень', 'верасень', 'кастрычнік',
|
||||
'лістапад', 'снежань'],
|
||||
SHORTMONTHS: ['сту', 'лют', 'сак', 'кра', 'мая', 'чэр',
|
||||
'ліп', 'жні', 'вер', 'кас', 'ліс', 'сне'],
|
||||
STANDALONESHORTMONTHS: ['сту', 'лют', 'сак', 'кра', 'май',
|
||||
'чэр', 'ліп', 'жні', 'вер', 'кас', 'ліс', 'сне'],
|
||||
WEEKDAYS: ['нядзеля', 'панядзелак', 'аўторак',
|
||||
'серада', 'чацвер', 'пятніца', 'субота'],
|
||||
STANDALONEWEEKDAYS: ['нядзеля', 'панядзелак',
|
||||
'аўторак', 'серада', 'чацвер', 'пятніца',
|
||||
'субота'],
|
||||
SHORTWEEKDAYS: ['нд', 'пн', 'аў', 'ср', 'чц', 'пт', 'сб'],
|
||||
STANDALONESHORTWEEKDAYS: ['нд', 'пн', 'аў', 'ср', 'чц', 'пт',
|
||||
'сб'],
|
||||
NARROWWEEKDAYS: ['н', 'п', 'а', 'с', 'ч', 'п', 'с'],
|
||||
STANDALONENARROWWEEKDAYS: ['н', 'п', 'а', 'с', 'ч', 'п', 'с'],
|
||||
SHORTQUARTERS: ['1-шы кв.', '2-гі кв.', '3-ці кв.',
|
||||
'4-ты кв.'],
|
||||
QUARTERS: ['1-шы квартал', '2-гі квартал',
|
||||
'3-ці квартал', '4-ты квартал'],
|
||||
AMPMS: ['да палудня', 'пасля палудня'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'd.M.y', 'd.M.yy'],
|
||||
TIMEFORMATS: ['HH.mm.ss zzzz', 'HH.mm.ss z', 'HH.mm.ss', 'HH.mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 6
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale bg.
|
||||
*/
|
||||
@@ -439,16 +491,10 @@ goog.i18n.DateTimeSymbols_bn = {
|
||||
NARROWWEEKDAYS: ['র', 'সো', 'ম', 'বু', 'বৃ', 'শু', 'শ'],
|
||||
STANDALONENARROWWEEKDAYS: ['র', 'সো', 'ম', 'বু', 'বৃ',
|
||||
'শু', 'শ'],
|
||||
SHORTQUARTERS: [
|
||||
'প্র. ত্রৈ. এক. চতুর্থাংশ',
|
||||
'দ্বি.ত্রৈ.এক. চতুর্থাংশ',
|
||||
'তৃ.ত্রৈ.এক.চতুর্থাংশ',
|
||||
'চ.ত্রৈ.এক চতুর্থাংশ'],
|
||||
QUARTERS: [
|
||||
'প্রথম ত্রৈমাসিকের এক চতুর্থাংশ',
|
||||
'দ্বিতীয় ত্রৈমাসিকের এক চতুর্থাংশ',
|
||||
'তৃতীয় ত্রৈমাসিকের এক চতুর্থাংশ',
|
||||
'চতুর্থ ত্রৈমাসিকের এক চতুর্থাংশ'],
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['ত্রৈমাসিক', 'ষাণ্মাসিক',
|
||||
'তৃতীয় চতুর্থাংশ',
|
||||
'চতুর্থ ত্রৈমাসিক'],
|
||||
AMPMS: ['am', 'pm'],
|
||||
DATEFORMATS: ['EEEE, d MMMM, y', 'd MMMM, y', 'd MMM, y', 'd/M/yy'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
@@ -497,6 +543,44 @@ goog.i18n.DateTimeSymbols_br = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale bs.
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_bs = {
|
||||
ERAS: ['p. n. e.', 'n. e.'],
|
||||
ERANAMES: ['Prije nove ere', 'Nove ere'],
|
||||
NARROWMONTHS: ['j', 'f', 'm', 'a', 'm', 'j', 'j', 'a', 's', 'o', 'n', 'd'],
|
||||
STANDALONENARROWMONTHS: ['j', 'f', 'm', 'a', 'm', 'j', 'j', 'a', 's', 'o',
|
||||
'n', 'd'],
|
||||
MONTHS: ['januar', 'februar', 'mart', 'april', 'maj', 'juni', 'juli',
|
||||
'august', 'septembar', 'oktobar', 'novembar', 'decembar'],
|
||||
STANDALONEMONTHS: ['januar', 'februar', 'mart', 'april', 'maj', 'juni',
|
||||
'juli', 'august', 'septembar', 'oktobar', 'novembar', 'decembar'],
|
||||
SHORTMONTHS: ['jan', 'feb', 'mar', 'apr', 'maj', 'jun', 'jul', 'aug', 'sep',
|
||||
'okt', 'nov', 'dec'],
|
||||
STANDALONESHORTMONTHS: ['jan', 'feb', 'mar', 'apr', 'maj', 'jun', 'jul',
|
||||
'aug', 'sep', 'okt', 'nov', 'dec'],
|
||||
WEEKDAYS: ['nedjelja', 'ponedjeljak', 'utorak', 'srijeda', 'četvrtak',
|
||||
'petak', 'subota'],
|
||||
STANDALONEWEEKDAYS: ['nedjelja', 'ponedjeljak', 'utorak', 'srijeda',
|
||||
'četvrtak', 'petak', 'subota'],
|
||||
SHORTWEEKDAYS: ['ned', 'pon', 'uto', 'sri', 'čet', 'pet', 'sub'],
|
||||
STANDALONESHORTWEEKDAYS: ['ned', 'pon', 'uto', 'sri', 'čet', 'pet', 'sub'],
|
||||
NARROWWEEKDAYS: ['N', 'P', 'U', 'S', 'Č', 'P', 'S'],
|
||||
STANDALONENARROWWEEKDAYS: ['n', 'p', 'u', 's', 'č', 'p', 's'],
|
||||
SHORTQUARTERS: ['K1', 'K2', 'K3', 'K4'],
|
||||
QUARTERS: ['Prvi kvartal', 'Drugi kvartal', 'Treći kvartal',
|
||||
'Četvrti kvartal'],
|
||||
AMPMS: ['prije podne', 'popodne'],
|
||||
DATEFORMATS: ['EEEE, dd. MMMM y.', 'dd. MMMM y.', 'dd. MMM. y.', 'dd.MM.yy.'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} \'u\' {0}', '{1} \'u\' {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 6
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale ca.
|
||||
*/
|
||||
@@ -507,8 +591,9 @@ goog.i18n.DateTimeSymbols_ca = {
|
||||
'NV', 'DS'],
|
||||
STANDALONENARROWMONTHS: ['GN', 'FB', 'MÇ', 'AB', 'MG', 'JN', 'JL', 'AG',
|
||||
'ST', 'OC', 'NV', 'DS'],
|
||||
MONTHS: ['gener', 'febrer', 'març', 'abril', 'maig', 'juny', 'juliol',
|
||||
'agost', 'setembre', 'octubre', 'novembre', 'desembre'],
|
||||
MONTHS: ['de gener', 'de febrer', 'de març', 'd’abril', 'de maig',
|
||||
'de juny', 'de juliol', 'd’agost', 'de setembre', 'd’octubre',
|
||||
'de novembre', 'de desembre'],
|
||||
STANDALONEMONTHS: ['gener', 'febrer', 'març', 'abril', 'maig', 'juny',
|
||||
'juliol', 'agost', 'setembre', 'octubre', 'novembre', 'desembre'],
|
||||
SHORTMONTHS: ['gen.', 'febr.', 'març', 'abr.', 'maig', 'juny', 'jul.', 'ag.',
|
||||
@@ -609,7 +694,7 @@ goog.i18n.DateTimeSymbols_cs = {
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1. čtvrtletí', '2. čtvrtletí', '3. čtvrtletí',
|
||||
'4. čtvrtletí'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
AMPMS: ['dopoledne', 'odpoledne'],
|
||||
DATEFORMATS: ['EEEE d. MMMM y', 'd. MMMM y', 'd. M. y', 'dd.MM.yy'],
|
||||
TIMEFORMATS: ['H:mm:ss zzzz', 'H:mm:ss z', 'H:mm:ss', 'H:mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
@@ -684,7 +769,7 @@ goog.i18n.DateTimeSymbols_da = {
|
||||
SHORTQUARTERS: ['1. kvt.', '2. kvt.', '3. kvt.', '4. kvt.'],
|
||||
QUARTERS: ['1. kvartal', '2. kvartal', '3. kvartal', '4. kvartal'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE \'den\' d. MMMM y', 'd. MMMM y', 'dd/MM/y', 'dd/MM/yy'],
|
||||
DATEFORMATS: ['EEEE \'den\' d. MMMM y', 'd. MMMM y', 'd. MMM y', 'dd/MM/y'],
|
||||
TIMEFORMATS: ['HH.mm.ss zzzz', 'HH.mm.ss z', 'HH.mm.ss', 'HH.mm'],
|
||||
DATETIMEFORMATS: ['{1} \'kl.\' {0}', '{1} \'kl.\' {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
@@ -758,7 +843,7 @@ goog.i18n.DateTimeSymbols_de_AT = {
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1. Quartal', '2. Quartal', '3. Quartal', '4. Quartal'],
|
||||
AMPMS: ['vorm.', 'nachm.'],
|
||||
DATEFORMATS: ['EEEE, dd. MMMM y', 'dd. MMMM y', 'dd. MMM y', 'dd.MM.yy'],
|
||||
DATEFORMATS: ['EEEE, d. MMMM y', 'd. MMMM y', 'dd.MM.y', 'dd.MM.yy'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} \'um\' {0}', '{1} \'um\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
@@ -882,10 +967,47 @@ goog.i18n.DateTimeSymbols_en_AU = {
|
||||
STANDALONENARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['am', 'pm'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'd MMM y', 'd/MM/y'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 5
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale en_CA.
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_en_CA = {
|
||||
ERAS: ['BC', 'AD'],
|
||||
ERANAMES: ['Before Christ', 'Anno Domini'],
|
||||
NARROWMONTHS: ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],
|
||||
STANDALONENARROWMONTHS: ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',
|
||||
'N', 'D'],
|
||||
MONTHS: ['January', 'February', 'March', 'April', 'May', 'June', 'July',
|
||||
'August', 'September', 'October', 'November', 'December'],
|
||||
STANDALONEMONTHS: ['January', 'February', 'March', 'April', 'May', 'June',
|
||||
'July', 'August', 'September', 'October', 'November', 'December'],
|
||||
SHORTMONTHS: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep',
|
||||
'Oct', 'Nov', 'Dec'],
|
||||
STANDALONESHORTMONTHS: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul',
|
||||
'Aug', 'Sep', 'Oct', 'Nov', 'Dec'],
|
||||
WEEKDAYS: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday',
|
||||
'Saturday'],
|
||||
STANDALONEWEEKDAYS: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday',
|
||||
'Friday', 'Saturday'],
|
||||
SHORTWEEKDAYS: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'],
|
||||
STANDALONESHORTWEEKDAYS: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'],
|
||||
NARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
STANDALONENARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE, MMMM d, y', 'MMMM d, y', 'MMM d, y', 'y-MM-dd'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 5
|
||||
@@ -919,7 +1041,7 @@ goog.i18n.DateTimeSymbols_en_GB = {
|
||||
STANDALONENARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['am', 'pm'],
|
||||
AMPMS: ['a.m.', 'p.m.'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'd MMM y', 'dd/MM/y'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
@@ -958,7 +1080,7 @@ goog.i18n.DateTimeSymbols_en_IE = {
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['a.m.', 'p.m.'],
|
||||
DATEFORMATS: ['EEEE d MMMM y', 'd MMMM y', 'd MMM y', 'dd/MM/y'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
@@ -993,7 +1115,7 @@ goog.i18n.DateTimeSymbols_en_IN = {
|
||||
STANDALONENARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['am', 'pm'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE d MMMM y', 'd MMMM y', 'dd-MMM-y', 'dd/MM/yy'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
@@ -1030,7 +1152,7 @@ goog.i18n.DateTimeSymbols_en_SG = {
|
||||
STANDALONENARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['am', 'pm'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'd MMM y', 'd/M/yy'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
@@ -1074,7 +1196,7 @@ goog.i18n.DateTimeSymbols_en_ZA = {
|
||||
SHORTQUARTERS: ['Q1', 'Q2', 'Q3', 'Q4'],
|
||||
QUARTERS: ['1st quarter', '2nd quarter', '3rd quarter', '4th quarter'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE dd MMMM y', 'dd MMMM y', 'dd MMM y', 'y/MM/dd'],
|
||||
DATEFORMATS: ['EEEE, dd MMMM y', 'dd MMMM y', 'dd MMM y', 'y/MM/dd'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1} \'at\' {0}', '{1} \'at\' {0}', '{1}, {0}', '{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
@@ -1088,7 +1210,7 @@ goog.i18n.DateTimeSymbols_en_ZA = {
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_es = {
|
||||
ERAS: ['a. C.', 'd. C.'],
|
||||
ERANAMES: ['antes de Cristo', 'anno Dómini'],
|
||||
ERANAMES: ['antes de Cristo', 'después de Cristo'],
|
||||
NARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],
|
||||
STANDALONENARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',
|
||||
'N', 'D'],
|
||||
@@ -1114,7 +1236,7 @@ goog.i18n.DateTimeSymbols_es = {
|
||||
'4.º trimestre'],
|
||||
AMPMS: ['a. m.', 'p. m.'],
|
||||
DATEFORMATS: ['EEEE, d \'de\' MMMM \'de\' y', 'd \'de\' MMMM \'de\' y',
|
||||
'd \'de\' MMM \'de\' y', 'd/M/yy'],
|
||||
'd MMM y', 'd/M/yy'],
|
||||
TIMEFORMATS: ['H:mm:ss (zzzz)', 'H:mm:ss z', 'H:mm:ss', 'H:mm'],
|
||||
DATETIMEFORMATS: ['{1}, {0}', '{1}, {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
@@ -1129,17 +1251,17 @@ goog.i18n.DateTimeSymbols_es = {
|
||||
goog.i18n.DateTimeSymbols_es_419 = {
|
||||
ERAS: ['a. C.', 'd. C.'],
|
||||
ERANAMES: ['antes de Cristo', 'después de Cristo'],
|
||||
NARROWMONTHS: ['e', 'f', 'm', 'a', 'm', 'j', 'j', 'a', 's', 'o', 'n', 'd'],
|
||||
NARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],
|
||||
STANDALONENARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',
|
||||
'N', 'D'],
|
||||
MONTHS: ['enero', 'febrero', 'marzo', 'abril', 'mayo', 'junio', 'julio',
|
||||
'agosto', 'setiembre', 'octubre', 'noviembre', 'diciembre'],
|
||||
'agosto', 'septiembre', 'octubre', 'noviembre', 'diciembre'],
|
||||
STANDALONEMONTHS: ['Enero', 'Febrero', 'Marzo', 'Abril', 'Mayo', 'Junio',
|
||||
'Julio', 'Agosto', 'Setiembre', 'Octubre', 'Noviembre', 'Diciembre'],
|
||||
'Julio', 'Agosto', 'Septiembre', 'Octubre', 'Noviembre', 'Diciembre'],
|
||||
SHORTMONTHS: ['ene.', 'feb.', 'mar.', 'abr.', 'may.', 'jun.', 'jul.', 'ago.',
|
||||
'set.', 'oct.', 'nov.', 'dic.'],
|
||||
'sept.', 'oct.', 'nov.', 'dic.'],
|
||||
STANDALONESHORTMONTHS: ['Ene.', 'Feb.', 'Mar.', 'Abr.', 'May.', 'Jun.',
|
||||
'Jul.', 'Ago.', 'Set.', 'Oct.', 'Nov.', 'Dic.'],
|
||||
'Jul.', 'Ago.', 'Sept.', 'Oct.', 'Nov.', 'Dic.'],
|
||||
WEEKDAYS: ['domingo', 'lunes', 'martes', 'miércoles', 'jueves', 'viernes',
|
||||
'sábado'],
|
||||
STANDALONEWEEKDAYS: ['Domingo', 'Lunes', 'Martes', 'Miércoles', 'Jueves',
|
||||
@@ -1149,12 +1271,12 @@ goog.i18n.DateTimeSymbols_es_419 = {
|
||||
'Sáb.'],
|
||||
NARROWWEEKDAYS: ['d', 'l', 'm', 'm', 'j', 'v', 's'],
|
||||
STANDALONENARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],
|
||||
SHORTQUARTERS: ['1.er trim.', '2.º trim.', '3.er trim.', '4.º trim.'],
|
||||
SHORTQUARTERS: ['T1', 'T2', 'T3', 'T4'],
|
||||
QUARTERS: ['1.er trimestre', '2.º trimestre', '3.er trimestre',
|
||||
'4.º trimestre'],
|
||||
AMPMS: ['a. m.', 'p. m.'],
|
||||
AMPMS: ['a. m.', 'p. m.'],
|
||||
DATEFORMATS: ['EEEE, d \'de\' MMMM \'de\' y', 'd \'de\' MMMM \'de\' y',
|
||||
'd \'de\' MMM \'de\' y', 'd/M/yy'],
|
||||
'd MMM y', 'd/M/yy'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1}, {0}', '{1}, {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
@@ -1169,6 +1291,86 @@ goog.i18n.DateTimeSymbols_es_419 = {
|
||||
goog.i18n.DateTimeSymbols_es_ES = goog.i18n.DateTimeSymbols_es;
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale es_MX.
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_es_MX = {
|
||||
ERAS: ['a. C.', 'd. C.'],
|
||||
ERANAMES: ['antes de Cristo', 'después de Cristo'],
|
||||
NARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],
|
||||
STANDALONENARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',
|
||||
'N', 'D'],
|
||||
MONTHS: ['enero', 'febrero', 'marzo', 'abril', 'mayo', 'junio', 'julio',
|
||||
'agosto', 'septiembre', 'octubre', 'noviembre', 'diciembre'],
|
||||
STANDALONEMONTHS: ['Enero', 'Febrero', 'Marzo', 'Abril', 'Mayo', 'Junio',
|
||||
'Julio', 'Agosto', 'Septiembre', 'Octubre', 'Noviembre', 'Diciembre'],
|
||||
SHORTMONTHS: ['ene', 'feb', 'mar', 'abr', 'may', 'jun', 'jul', 'ago', 'sep',
|
||||
'oct', 'nov', 'dic'],
|
||||
STANDALONESHORTMONTHS: ['Ene.', 'Feb.', 'Mar.', 'Abr.', 'May.', 'Jun.',
|
||||
'Jul.', 'Ago.', 'Sept.', 'Oct.', 'Nov.', 'Dic.'],
|
||||
WEEKDAYS: ['domingo', 'lunes', 'martes', 'miércoles', 'jueves', 'viernes',
|
||||
'sábado'],
|
||||
STANDALONEWEEKDAYS: ['Domingo', 'Lunes', 'Martes', 'Miércoles', 'Jueves',
|
||||
'Viernes', 'Sábado'],
|
||||
SHORTWEEKDAYS: ['dom.', 'lun.', 'mar.', 'mié.', 'jue.', 'vie.', 'sáb.'],
|
||||
STANDALONESHORTWEEKDAYS: ['Dom.', 'Lun.', 'Mar.', 'Mié.', 'Jue.', 'Vie.',
|
||||
'Sáb.'],
|
||||
NARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],
|
||||
STANDALONENARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],
|
||||
SHORTQUARTERS: ['1er. trim.', '2º. trim.', '3er. trim.', '4º trim.'],
|
||||
QUARTERS: ['1er. trimestre', '2º. trimestre', '3er. trimestre',
|
||||
'4º trimestre'],
|
||||
AMPMS: ['a.m.', 'p.m.'],
|
||||
DATEFORMATS: ['EEEE, d \'de\' MMMM \'de\' y', 'd \'de\' MMMM \'de\' y',
|
||||
'dd/MM/y', 'dd/MM/yy'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1}, {0}', '{1}, {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 5
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale es_US.
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_es_US = {
|
||||
ERAS: ['a. C.', 'd. C.'],
|
||||
ERANAMES: ['antes de Cristo', 'después de Cristo'],
|
||||
NARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],
|
||||
STANDALONENARROWMONTHS: ['E', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',
|
||||
'N', 'D'],
|
||||
MONTHS: ['enero', 'febrero', 'marzo', 'abril', 'mayo', 'junio', 'julio',
|
||||
'agosto', 'septiembre', 'octubre', 'noviembre', 'diciembre'],
|
||||
STANDALONEMONTHS: ['Enero', 'Febrero', 'Marzo', 'Abril', 'Mayo', 'Junio',
|
||||
'Julio', 'Agosto', 'Septiembre', 'Octubre', 'Noviembre', 'Diciembre'],
|
||||
SHORTMONTHS: ['ene.', 'feb.', 'mar.', 'abr.', 'may.', 'jun.', 'jul.', 'ago.',
|
||||
'sept.', 'oct.', 'nov.', 'dic.'],
|
||||
STANDALONESHORTMONTHS: ['Ene.', 'Feb.', 'Mar.', 'Abr.', 'May.', 'Jun.',
|
||||
'Jul.', 'Ago.', 'Sept.', 'Oct.', 'Nov.', 'Dic.'],
|
||||
WEEKDAYS: ['domingo', 'lunes', 'martes', 'miércoles', 'jueves', 'viernes',
|
||||
'sábado'],
|
||||
STANDALONEWEEKDAYS: ['Domingo', 'Lunes', 'Martes', 'Miércoles', 'Jueves',
|
||||
'Viernes', 'Sábado'],
|
||||
SHORTWEEKDAYS: ['dom.', 'lun.', 'mar.', 'mié.', 'jue.', 'vie.', 'sáb.'],
|
||||
STANDALONESHORTWEEKDAYS: ['Dom.', 'Lun.', 'Mar.', 'Mié.', 'Jue.', 'Vie.',
|
||||
'Sáb.'],
|
||||
NARROWWEEKDAYS: ['d', 'l', 'm', 'm', 'j', 'v', 's'],
|
||||
STANDALONENARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],
|
||||
SHORTQUARTERS: ['T1', 'T2', 'T3', 'T4'],
|
||||
QUARTERS: ['1.er trimestre', '2.º trimestre', '3.er trimestre',
|
||||
'4.º trimestre'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE, d \'de\' MMMM \'de\' y', 'd \'de\' MMMM \'de\' y',
|
||||
'd MMM y', 'd/M/yy'],
|
||||
TIMEFORMATS: ['h:mm:ss a zzzz', 'h:mm:ss a z', 'h:mm:ss a', 'h:mm a'],
|
||||
DATETIMEFORMATS: ['{1}, {0}', '{1}, {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 5
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale et.
|
||||
*/
|
||||
@@ -1327,7 +1529,8 @@ goog.i18n.DateTimeSymbols_fi = {
|
||||
AMPMS: ['ap.', 'ip.'],
|
||||
DATEFORMATS: ['cccc d. MMMM y', 'd. MMMM y', 'd.M.y', 'd.M.y'],
|
||||
TIMEFORMATS: ['H.mm.ss zzzz', 'H.mm.ss z', 'H.mm.ss', 'H.mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
DATETIMEFORMATS: ['{1} \'klo\' {0}', '{1} \'klo\' {0}', '{1} \'klo\' {0}',
|
||||
'{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 3
|
||||
@@ -1440,10 +1643,9 @@ goog.i18n.DateTimeSymbols_fr_CA = {
|
||||
SHORTQUARTERS: ['T1', 'T2', 'T3', 'T4'],
|
||||
QUARTERS: ['1er trimestre', '2e trimestre', '3e trimestre', '4e trimestre'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE d MMMM y', 'd MMMM y', 'y-MM-dd', 'yy-MM-dd'],
|
||||
TIMEFORMATS: ['HH \'h\' mm \'min\' ss \'s\' zzzz', 'HH:mm:ss z', 'HH:mm:ss',
|
||||
'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} \'à\' {0}', '{1} \'à\' {0}', '{1} {0}', '{1} {0}'],
|
||||
DATEFORMATS: ['EEEE d MMMM y', 'd MMMM y', 'd MMM y', 'yy-MM-dd'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 5
|
||||
@@ -1697,7 +1899,7 @@ goog.i18n.DateTimeSymbols_he = {
|
||||
QUARTERS: ['רבעון 1', 'רבעון 2', 'רבעון 3', 'רבעון 4'],
|
||||
AMPMS: ['לפנה״צ', 'אחה״צ'],
|
||||
DATEFORMATS: ['EEEE, d בMMMM y', 'd בMMMM y', 'd בMMM y', 'd.M.y'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
TIMEFORMATS: ['H:mm:ss zzzz', 'H:mm:ss z', 'H:mm:ss', 'H:mm'],
|
||||
DATETIMEFORMATS: ['{1} בשעה {0}', '{1} בשעה {0}', '{1}, {0}',
|
||||
'{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
@@ -2073,7 +2275,7 @@ goog.i18n.DateTimeSymbols_iw = {
|
||||
QUARTERS: ['רבעון 1', 'רבעון 2', 'רבעון 3', 'רבעון 4'],
|
||||
AMPMS: ['לפנה״צ', 'אחה״צ'],
|
||||
DATEFORMATS: ['EEEE, d בMMMM y', 'd בMMMM y', 'd בMMM y', 'd.M.y'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
TIMEFORMATS: ['H:mm:ss zzzz', 'H:mm:ss z', 'H:mm:ss', 'H:mm'],
|
||||
DATETIMEFORMATS: ['{1} בשעה {0}', '{1} בשעה {0}', '{1}, {0}',
|
||||
'{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
@@ -2941,7 +3143,7 @@ goog.i18n.DateTimeSymbols_my = {
|
||||
'တတိယ သုံးလပတ်',
|
||||
'စတုတ္ထ သုံးလပတ်'],
|
||||
AMPMS: ['နံနက်', 'ညနေ'],
|
||||
DATEFORMATS: ['EEEE, dd MMMM y', 'd MMMM y', 'd MMM y', 'dd-MM-yy'],
|
||||
DATEFORMATS: ['EEEE၊ dd MMMM y', 'd MMMM y', 'd MMM y', 'dd-MM-yy'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1}မှာ {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
@@ -2999,7 +3201,7 @@ goog.i18n.DateTimeSymbols_ne = {
|
||||
STANDALONENARROWMONTHS: ['१', '२', '३', '४', '५', '६', '७',
|
||||
'८', '९', '१०', '११', '१२'],
|
||||
MONTHS: ['जनवरी', 'फेब्रुअरी', 'मार्च',
|
||||
'अप्रिल', 'मे', 'जुन', 'जुलाई',
|
||||
'अप्रिल', 'मई', 'जुन', 'जुलाई',
|
||||
'अगस्ट', 'सेप्टेम्बर',
|
||||
'अक्टोबर', 'नोभेम्बर',
|
||||
'डिसेम्बर'],
|
||||
@@ -3019,10 +3221,10 @@ goog.i18n.DateTimeSymbols_ne = {
|
||||
'अक्टोबर', 'नोभेम्बर',
|
||||
'डिसेम्बर'],
|
||||
WEEKDAYS: ['आइतबार', 'सोमबार',
|
||||
'मङ्गलबार', 'बुधबार', 'बिहीबार',
|
||||
'मङ्गलबार', 'बुधबार', 'बिहिबार',
|
||||
'शुक्रबार', 'शनिबार'],
|
||||
STANDALONEWEEKDAYS: ['आइतबार', 'सोमबार',
|
||||
'मङ्गलबार', 'बुधबार', 'बिहीबार',
|
||||
'मङ्गलबार', 'बुधबार', 'बिहिबार',
|
||||
'शुक्रबार', 'शनिबार'],
|
||||
SHORTWEEKDAYS: ['आइत', 'सोम', 'मङ्गल', 'बुध',
|
||||
'बिही', 'शुक्र', 'शनि'],
|
||||
@@ -3036,8 +3238,7 @@ goog.i18n.DateTimeSymbols_ne = {
|
||||
'चौथो सत्र'],
|
||||
QUARTERS: ['पहिलो सत्र', 'दोस्रो सत्र',
|
||||
'तेस्रो सत्र', 'चौथो सत्र'],
|
||||
AMPMS: ['पूर्व मध्यान्ह',
|
||||
'उत्तर मध्यान्ह'],
|
||||
AMPMS: ['पूर्वाह्न', 'अपराह्न'],
|
||||
DATEFORMATS: ['y MMMM d, EEEE', 'y MMMM d', 'y MMM d', 'y-MM-dd'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1}, {0}', '{1}, {0}'],
|
||||
@@ -3265,7 +3466,7 @@ goog.i18n.DateTimeSymbols_pl = {
|
||||
SHORTQUARTERS: ['K1', 'K2', 'K3', 'K4'],
|
||||
QUARTERS: ['I kwartał', 'II kwartał', 'III kwartał', 'IV kwartał'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'd MMM y', 'dd.MM.y'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'dd.MM.y', 'dd.MM.y'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1}, {0}', '{1}, {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
@@ -3330,12 +3531,12 @@ goog.i18n.DateTimeSymbols_pt_PT = {
|
||||
'N', 'D'],
|
||||
MONTHS: ['janeiro', 'fevereiro', 'março', 'abril', 'maio', 'junho', 'julho',
|
||||
'agosto', 'setembro', 'outubro', 'novembro', 'dezembro'],
|
||||
STANDALONEMONTHS: ['Janeiro', 'Fevereiro', 'Março', 'Abril', 'Maio', 'Junho',
|
||||
'Julho', 'Agosto', 'Setembro', 'Outubro', 'Novembro', 'Dezembro'],
|
||||
STANDALONEMONTHS: ['janeiro', 'fevereiro', 'março', 'abril', 'maio', 'junho',
|
||||
'julho', 'agosto', 'setembro', 'outubro', 'novembro', 'dezembro'],
|
||||
SHORTMONTHS: ['jan', 'fev', 'mar', 'abr', 'mai', 'jun', 'jul', 'ago', 'set',
|
||||
'out', 'nov', 'dez'],
|
||||
STANDALONESHORTMONTHS: ['Jan', 'Fev', 'Mar', 'Abr', 'Mai', 'Jun', 'Jul',
|
||||
'Ago', 'Set', 'Out', 'Nov', 'Dez'],
|
||||
STANDALONESHORTMONTHS: ['jan', 'fev', 'mar', 'abr', 'mai', 'jun', 'jul',
|
||||
'ago', 'set', 'out', 'nov', 'dez'],
|
||||
WEEKDAYS: ['domingo', 'segunda-feira', 'terça-feira', 'quarta-feira',
|
||||
'quinta-feira', 'sexta-feira', 'sábado'],
|
||||
STANDALONEWEEKDAYS: ['domingo', 'segunda-feira', 'terça-feira',
|
||||
@@ -3570,7 +3771,7 @@ goog.i18n.DateTimeSymbols_sl = {
|
||||
'4. četrtletje'],
|
||||
AMPMS: ['dop.', 'pop.'],
|
||||
DATEFORMATS: ['EEEE, dd. MMMM y', 'dd. MMMM y', 'd. MMM y', 'd. MM. yy'],
|
||||
TIMEFORMATS: ['HH.mm.ss zzzz', 'HH.mm.ss z', 'HH.mm.ss', 'HH.mm'],
|
||||
TIMEFORMATS: ['HH:mm:ss zzzz', 'HH:mm:ss z', 'HH:mm:ss', 'HH:mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
@@ -3661,6 +3862,44 @@ goog.i18n.DateTimeSymbols_sr = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale sr_Latn.
|
||||
*/
|
||||
goog.i18n.DateTimeSymbols_sr_Latn = {
|
||||
ERAS: ['p. n. e.', 'n. e.'],
|
||||
ERANAMES: ['Pre nove ere', 'Nove ere'],
|
||||
NARROWMONTHS: ['j', 'f', 'm', 'a', 'm', 'j', 'j', 'a', 's', 'o', 'n', 'd'],
|
||||
STANDALONENARROWMONTHS: ['j', 'f', 'm', 'a', 'm', 'j', 'j', 'a', 's', 'o',
|
||||
'n', 'd'],
|
||||
MONTHS: ['januar', 'februar', 'mart', 'april', 'maj', 'jun', 'jul', 'avgust',
|
||||
'septembar', 'oktobar', 'novembar', 'decembar'],
|
||||
STANDALONEMONTHS: ['januar', 'februar', 'mart', 'april', 'maj', 'jun', 'jul',
|
||||
'avgust', 'septembar', 'oktobar', 'novembar', 'decembar'],
|
||||
SHORTMONTHS: ['jan', 'feb', 'mar', 'apr', 'maj', 'jun', 'jul', 'avg', 'sep',
|
||||
'okt', 'nov', 'dec'],
|
||||
STANDALONESHORTMONTHS: ['jan', 'feb', 'mar', 'apr', 'maj', 'jun', 'jul',
|
||||
'avg', 'sep', 'okt', 'nov', 'dec'],
|
||||
WEEKDAYS: ['nedelja', 'ponedeljak', 'utorak', 'sreda', 'četvrtak', 'petak',
|
||||
'subota'],
|
||||
STANDALONEWEEKDAYS: ['nedelja', 'ponedeljak', 'utorak', 'sreda', 'četvrtak',
|
||||
'petak', 'subota'],
|
||||
SHORTWEEKDAYS: ['ned', 'pon', 'uto', 'sre', 'čet', 'pet', 'sub'],
|
||||
STANDALONESHORTWEEKDAYS: ['ned', 'pon', 'uto', 'sre', 'čet', 'pet', 'sub'],
|
||||
NARROWWEEKDAYS: ['n', 'p', 'u', 's', 'č', 'p', 's'],
|
||||
STANDALONENARROWWEEKDAYS: ['n', 'p', 'u', 's', 'č', 'p', 's'],
|
||||
SHORTQUARTERS: ['K1', 'K2', 'K3', 'K4'],
|
||||
QUARTERS: ['Prvo tromesečje', 'Drugo tromesečje', 'Treće tromesečje',
|
||||
'Četvrto tromesečje'],
|
||||
AMPMS: ['pre podne', 'po podne'],
|
||||
DATEFORMATS: ['EEEE, dd. MMMM y.', 'dd. MMMM y.', 'dd.MM.y.', 'd.M.yy.'],
|
||||
TIMEFORMATS: ['HH.mm.ss zzzz', 'HH.mm.ss z', 'HH.mm.ss', 'HH.mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 0,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
FIRSTWEEKCUTOFFDAY: 6
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Date/time formatting symbols for locale sv.
|
||||
*/
|
||||
@@ -3726,7 +3965,7 @@ goog.i18n.DateTimeSymbols_sw = {
|
||||
'Alhamisi', 'Ijumaa', 'Jumamosi'],
|
||||
NARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
STANDALONENARROWWEEKDAYS: ['S', 'M', 'T', 'W', 'T', 'F', 'S'],
|
||||
SHORTQUARTERS: ['Robo ya 1', 'Robo ya 2', 'Robo ya 3', 'Robo ya 4'],
|
||||
SHORTQUARTERS: ['R1', 'R2', 'R3', 'R4'],
|
||||
QUARTERS: ['Robo ya 1', 'Robo ya 2', 'Robo ya 3', 'Robo ya 4'],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
DATEFORMATS: ['EEEE, d MMMM y', 'd MMMM y', 'd MMM y', 'dd/MM/y'],
|
||||
@@ -4189,7 +4428,7 @@ goog.i18n.DateTimeSymbols_zh = {
|
||||
QUARTERS: ['第一季度', '第二季度', '第三季度', '第四季度'],
|
||||
AMPMS: ['上午', '下午'],
|
||||
DATEFORMATS: ['y年M月d日EEEE', 'y年M月d日', 'y年M月d日', 'yy/M/d'],
|
||||
TIMEFORMATS: ['zzzzah:mm:ss', 'zah:mm:ss', 'ah:mm:ss', 'ah:mm'],
|
||||
TIMEFORMATS: ['zzzz ah:mm:ss', 'z ah:mm:ss', 'ah:mm:ss', 'ah:mm'],
|
||||
DATETIMEFORMATS: ['{1} {0}', '{1} {0}', '{1} {0}', '{1} {0}'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
@@ -4330,12 +4569,16 @@ if (goog.LOCALE == 'af') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_ar;
|
||||
} else if (goog.LOCALE == 'az') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_az;
|
||||
} else if (goog.LOCALE == 'be') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_be;
|
||||
} else if (goog.LOCALE == 'bg') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_bg;
|
||||
} else if (goog.LOCALE == 'bn') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_bn;
|
||||
} else if (goog.LOCALE == 'br') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_br;
|
||||
} else if (goog.LOCALE == 'bs') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_bs;
|
||||
} else if (goog.LOCALE == 'ca') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_ca;
|
||||
} else if (goog.LOCALE == 'chr') {
|
||||
@@ -4358,6 +4601,8 @@ if (goog.LOCALE == 'af') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_en;
|
||||
} else if (goog.LOCALE == 'en_AU' || goog.LOCALE == 'en-AU') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_en_AU;
|
||||
} else if (goog.LOCALE == 'en_CA' || goog.LOCALE == 'en-CA') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_en_CA;
|
||||
} else if (goog.LOCALE == 'en_GB' || goog.LOCALE == 'en-GB') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_en_GB;
|
||||
} else if (goog.LOCALE == 'en_IE' || goog.LOCALE == 'en-IE') {
|
||||
@@ -4376,6 +4621,10 @@ if (goog.LOCALE == 'af') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_es_419;
|
||||
} else if (goog.LOCALE == 'es_ES' || goog.LOCALE == 'es-ES') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_es;
|
||||
} else if (goog.LOCALE == 'es_MX' || goog.LOCALE == 'es-MX') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_es_MX;
|
||||
} else if (goog.LOCALE == 'es_US' || goog.LOCALE == 'es-US') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_es_US;
|
||||
} else if (goog.LOCALE == 'et') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_et;
|
||||
} else if (goog.LOCALE == 'eu') {
|
||||
@@ -4492,6 +4741,8 @@ if (goog.LOCALE == 'af') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_sq;
|
||||
} else if (goog.LOCALE == 'sr') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_sr;
|
||||
} else if (goog.LOCALE == 'sr_Latn' || goog.LOCALE == 'sr-Latn') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_sr_Latn;
|
||||
} else if (goog.LOCALE == 'sv') {
|
||||
goog.i18n.DateTimeSymbols = goog.i18n.DateTimeSymbols_sv;
|
||||
} else if (goog.LOCALE == 'sw') {
|
||||
|
||||
+541
-1281
File diff suppressed because it is too large
Load Diff
@@ -18,7 +18,7 @@
|
||||
* This file is autogenerated by script:
|
||||
* http://go/generate_number_constants.py
|
||||
* using the --for_closure flag.
|
||||
* File generated from CLDR ver. 26
|
||||
* File generated from CLDR ver. 27.0.1
|
||||
*
|
||||
* To reduce the file size (which may cause issues in some JS
|
||||
* developing environments), this file will only contain locales
|
||||
@@ -41,14 +41,21 @@ goog.provide('goog.i18n.NumberFormatSymbols_am');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_am_ET');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ar');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ar_001');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ar_EG');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_az');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_az_Latn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_az_Latn_AZ');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_be');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_be_BY');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bg');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bg_BG');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bn_BD');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_br');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_br_FR');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bs');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bs_Latn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_bs_Latn_BA');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ca');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ca_AD');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ca_ES');
|
||||
@@ -71,11 +78,13 @@ goog.provide('goog.i18n.NumberFormatSymbols_de_CH');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_de_DE');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_de_LU');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_el');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_el_CY');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_el_GR');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_001');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_AS');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_AU');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_CA');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_DG');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_FM');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_en_GB');
|
||||
@@ -100,6 +109,8 @@ goog.provide('goog.i18n.NumberFormatSymbols_es_419');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_es_EA');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_es_ES');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_es_IC');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_es_MX');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_es_US');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_et');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_et_EE');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_eu');
|
||||
@@ -157,6 +168,7 @@ goog.provide('goog.i18n.NumberFormatSymbols_ja_JP');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ka');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ka_GE');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_kk');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_kk_Cyrl');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_kk_Cyrl_KZ');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_km');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_km_KH');
|
||||
@@ -165,6 +177,7 @@ goog.provide('goog.i18n.NumberFormatSymbols_kn_IN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ko');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ko_KR');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ky');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ky_Cyrl');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ky_Cyrl_KG');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ln');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ln_CD');
|
||||
@@ -179,10 +192,12 @@ goog.provide('goog.i18n.NumberFormatSymbols_mk_MK');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ml');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ml_IN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mn_Cyrl');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mn_Cyrl_MN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mr');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mr_IN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ms');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ms_Latn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ms_Latn_MY');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mt');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_mt_MT');
|
||||
@@ -200,6 +215,7 @@ goog.provide('goog.i18n.NumberFormatSymbols_no_NO');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_or');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_or_IN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_pa');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_pa_Guru');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_pa_Guru_IN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_pl');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_pl_PL');
|
||||
@@ -219,7 +235,10 @@ goog.provide('goog.i18n.NumberFormatSymbols_sl_SI');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sq');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sq_AL');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sr');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sr_Cyrl');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sr_Cyrl_RS');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sr_Latn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sr_Latn_RS');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sv');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sv_SE');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_sw');
|
||||
@@ -238,12 +257,14 @@ goog.provide('goog.i18n.NumberFormatSymbols_uk_UA');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ur');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_ur_PK');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_uz');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_uz_Latn');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_uz_Latn_UZ');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_vi');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_vi_VN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zh');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zh_CN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zh_HK');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zh_Hans');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zh_Hans_CN');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zh_TW');
|
||||
goog.provide('goog.i18n.NumberFormatSymbols_zu');
|
||||
@@ -340,6 +361,13 @@ goog.i18n.NumberFormatSymbols_ar = {
|
||||
goog.i18n.NumberFormatSymbols_ar_001 = goog.i18n.NumberFormatSymbols_ar;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale ar_EG.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_ar_EG = goog.i18n.NumberFormatSymbols_ar;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale az.
|
||||
* @enum {string}
|
||||
@@ -363,6 +391,13 @@ goog.i18n.NumberFormatSymbols_az = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale az_Latn.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_az_Latn = goog.i18n.NumberFormatSymbols_az;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale az_Latn_AZ.
|
||||
* @enum {string}
|
||||
@@ -370,6 +405,36 @@ goog.i18n.NumberFormatSymbols_az = {
|
||||
goog.i18n.NumberFormatSymbols_az_Latn_AZ = goog.i18n.NumberFormatSymbols_az;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale be.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_be = {
|
||||
DECIMAL_SEP: ',',
|
||||
GROUP_SEP: '\u00A0',
|
||||
PERCENT: '%',
|
||||
ZERO_DIGIT: '0',
|
||||
PLUS_SIGN: '+',
|
||||
MINUS_SIGN: '-',
|
||||
EXP_SYMBOL: 'E',
|
||||
PERMILL: '\u2030',
|
||||
INFINITY: '\u221E',
|
||||
NAN: 'NaN',
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0%',
|
||||
CURRENCY_PATTERN: '\u00A4#,##0.00',
|
||||
DEF_CURRENCY_CODE: 'BYR'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale be_BY.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_be_BY = goog.i18n.NumberFormatSymbols_be;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale bg.
|
||||
* @enum {string}
|
||||
@@ -460,6 +525,43 @@ goog.i18n.NumberFormatSymbols_br = {
|
||||
goog.i18n.NumberFormatSymbols_br_FR = goog.i18n.NumberFormatSymbols_br;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale bs.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_bs = {
|
||||
DECIMAL_SEP: ',',
|
||||
GROUP_SEP: '.',
|
||||
PERCENT: '%',
|
||||
ZERO_DIGIT: '0',
|
||||
PLUS_SIGN: '+',
|
||||
MINUS_SIGN: '-',
|
||||
EXP_SYMBOL: 'E',
|
||||
PERMILL: '\u2030',
|
||||
INFINITY: '\u221E',
|
||||
NAN: 'NaN',
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0%',
|
||||
CURRENCY_PATTERN: '#,##0.00\u00A0\u00A4',
|
||||
DEF_CURRENCY_CODE: 'BAM'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale bs_Latn.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_bs_Latn = goog.i18n.NumberFormatSymbols_bs;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale bs_Latn_BA.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_bs_Latn_BA = goog.i18n.NumberFormatSymbols_bs;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale ca.
|
||||
* @enum {string}
|
||||
@@ -758,6 +860,13 @@ goog.i18n.NumberFormatSymbols_el = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale el_CY.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_el_CY = goog.i18n.NumberFormatSymbols_el;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale el_GR.
|
||||
* @enum {string}
|
||||
@@ -825,6 +934,29 @@ goog.i18n.NumberFormatSymbols_en_AU = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale en_CA.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_en_CA = {
|
||||
DECIMAL_SEP: '.',
|
||||
GROUP_SEP: ',',
|
||||
PERCENT: '%',
|
||||
ZERO_DIGIT: '0',
|
||||
PLUS_SIGN: '+',
|
||||
MINUS_SIGN: '-',
|
||||
EXP_SYMBOL: 'E',
|
||||
PERMILL: '\u2030',
|
||||
INFINITY: '\u221E',
|
||||
NAN: 'NaN',
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0%',
|
||||
CURRENCY_PATTERN: '\u00A4#,##0.00',
|
||||
DEF_CURRENCY_CODE: 'CAD'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale en_DG.
|
||||
* @enum {string}
|
||||
@@ -1105,6 +1237,52 @@ goog.i18n.NumberFormatSymbols_es_ES = goog.i18n.NumberFormatSymbols_es;
|
||||
goog.i18n.NumberFormatSymbols_es_IC = goog.i18n.NumberFormatSymbols_es;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale es_MX.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_es_MX = {
|
||||
DECIMAL_SEP: '.',
|
||||
GROUP_SEP: ',',
|
||||
PERCENT: '%',
|
||||
ZERO_DIGIT: '0',
|
||||
PLUS_SIGN: '+',
|
||||
MINUS_SIGN: '-',
|
||||
EXP_SYMBOL: 'E',
|
||||
PERMILL: '\u2030',
|
||||
INFINITY: '\u221E',
|
||||
NAN: 'NaN',
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0%',
|
||||
CURRENCY_PATTERN: '\u00A4#,##0.00',
|
||||
DEF_CURRENCY_CODE: 'MXN'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale es_US.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_es_US = {
|
||||
DECIMAL_SEP: '.',
|
||||
GROUP_SEP: ',',
|
||||
PERCENT: '%',
|
||||
ZERO_DIGIT: '0',
|
||||
PLUS_SIGN: '+',
|
||||
MINUS_SIGN: '-',
|
||||
EXP_SYMBOL: 'E',
|
||||
PERMILL: '\u2030',
|
||||
INFINITY: '\u221E',
|
||||
NAN: 'NaN',
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0\u00A0%',
|
||||
CURRENCY_PATTERN: '\u00A4#,##0.00',
|
||||
DEF_CURRENCY_CODE: 'USD'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale et.
|
||||
* @enum {string}
|
||||
@@ -1905,6 +2083,13 @@ goog.i18n.NumberFormatSymbols_kk = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale kk_Cyrl.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_kk_Cyrl = goog.i18n.NumberFormatSymbols_kk;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale kk_Cyrl_KZ.
|
||||
* @enum {string}
|
||||
@@ -2025,6 +2210,13 @@ goog.i18n.NumberFormatSymbols_ky = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale ky_Cyrl.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_ky_Cyrl = goog.i18n.NumberFormatSymbols_ky;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale ky_Cyrl_KG.
|
||||
* @enum {string}
|
||||
@@ -2236,6 +2428,13 @@ goog.i18n.NumberFormatSymbols_mn = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale mn_Cyrl.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_mn_Cyrl = goog.i18n.NumberFormatSymbols_mn;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale mn_Cyrl_MN.
|
||||
* @enum {string}
|
||||
@@ -2296,6 +2495,13 @@ goog.i18n.NumberFormatSymbols_ms = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale ms_Latn.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_ms_Latn = goog.i18n.NumberFormatSymbols_ms;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale ms_Latn_MY.
|
||||
* @enum {string}
|
||||
@@ -2449,7 +2655,7 @@ goog.i18n.NumberFormatSymbols_nl = {
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0%',
|
||||
CURRENCY_PATTERN: '\u00A4\u00A0#,##0.00;\u00A4\u00A0#,##0.00-',
|
||||
CURRENCY_PATTERN: '\u00A4\u00A0#,##0.00;\u00A4\u00A0-#,##0.00',
|
||||
DEF_CURRENCY_CODE: 'EUR'
|
||||
};
|
||||
|
||||
@@ -2544,6 +2750,13 @@ goog.i18n.NumberFormatSymbols_pa = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale pa_Guru.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_pa_Guru = goog.i18n.NumberFormatSymbols_pa;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale pa_Guru_IN.
|
||||
* @enum {string}
|
||||
@@ -2837,6 +3050,13 @@ goog.i18n.NumberFormatSymbols_sr = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale sr_Cyrl.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_sr_Cyrl = goog.i18n.NumberFormatSymbols_sr;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale sr_Cyrl_RS.
|
||||
* @enum {string}
|
||||
@@ -2844,6 +3064,37 @@ goog.i18n.NumberFormatSymbols_sr = {
|
||||
goog.i18n.NumberFormatSymbols_sr_Cyrl_RS = goog.i18n.NumberFormatSymbols_sr;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale sr_Latn.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_sr_Latn = {
|
||||
DECIMAL_SEP: ',',
|
||||
GROUP_SEP: '.',
|
||||
PERCENT: '%',
|
||||
ZERO_DIGIT: '0',
|
||||
PLUS_SIGN: '+',
|
||||
MINUS_SIGN: '-',
|
||||
EXP_SYMBOL: 'E',
|
||||
PERMILL: '\u2030',
|
||||
INFINITY: '\u221E',
|
||||
NAN: 'NaN',
|
||||
DECIMAL_PATTERN: '#,##0.###',
|
||||
SCIENTIFIC_PATTERN: '#E0',
|
||||
PERCENT_PATTERN: '#,##0%',
|
||||
CURRENCY_PATTERN: '#,##0.00\u00A0\u00A4',
|
||||
DEF_CURRENCY_CODE: 'RSD'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale sr_Latn_RS.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_sr_Latn_RS =
|
||||
goog.i18n.NumberFormatSymbols_sr_Latn;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale sv.
|
||||
* @enum {string}
|
||||
@@ -3130,6 +3381,13 @@ goog.i18n.NumberFormatSymbols_uz = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale uz_Latn.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_uz_Latn = goog.i18n.NumberFormatSymbols_uz;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale uz_Latn_UZ.
|
||||
* @enum {string}
|
||||
@@ -3220,6 +3478,13 @@ goog.i18n.NumberFormatSymbols_zh_HK = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale zh_Hans.
|
||||
* @enum {string}
|
||||
*/
|
||||
goog.i18n.NumberFormatSymbols_zh_Hans = goog.i18n.NumberFormatSymbols_zh;
|
||||
|
||||
|
||||
/**
|
||||
* Number formatting symbols for locale zh_Hans_CN.
|
||||
* @enum {string}
|
||||
@@ -3309,14 +3574,30 @@ if (goog.LOCALE == 'ar_001' || goog.LOCALE == 'ar-001') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ar;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'ar_EG' || goog.LOCALE == 'ar-EG') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ar;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'az') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_az;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'az_Latn' || goog.LOCALE == 'az-Latn') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_az;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'az_Latn_AZ' || goog.LOCALE == 'az-Latn-AZ') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_az;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'be') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_be;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'be_BY' || goog.LOCALE == 'be-BY') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_be;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'bg') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_bg;
|
||||
}
|
||||
@@ -3341,6 +3622,18 @@ if (goog.LOCALE == 'br_FR' || goog.LOCALE == 'br-FR') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_br;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'bs') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_bs;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'bs_Latn' || goog.LOCALE == 'bs-Latn') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_bs;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'bs_Latn_BA' || goog.LOCALE == 'bs-Latn-BA') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_bs;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'ca') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ca;
|
||||
}
|
||||
@@ -3429,6 +3722,10 @@ if (goog.LOCALE == 'el') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_el;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'el_CY' || goog.LOCALE == 'el-CY') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_el;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'el_GR' || goog.LOCALE == 'el-GR') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_el;
|
||||
}
|
||||
@@ -3449,6 +3746,10 @@ if (goog.LOCALE == 'en_AU' || goog.LOCALE == 'en-AU') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_en_AU;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'en_CA' || goog.LOCALE == 'en-CA') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_en_CA;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'en_DG' || goog.LOCALE == 'en-DG') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_en;
|
||||
}
|
||||
@@ -3545,6 +3846,14 @@ if (goog.LOCALE == 'es_IC' || goog.LOCALE == 'es-IC') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_es;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'es_MX' || goog.LOCALE == 'es-MX') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_es_MX;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'es_US' || goog.LOCALE == 'es-US') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_es_US;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'et') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_et;
|
||||
}
|
||||
@@ -3773,6 +4082,10 @@ if (goog.LOCALE == 'kk') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_kk;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'kk_Cyrl' || goog.LOCALE == 'kk-Cyrl') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_kk;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'kk_Cyrl_KZ' || goog.LOCALE == 'kk-Cyrl-KZ') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_kk;
|
||||
}
|
||||
@@ -3805,6 +4118,10 @@ if (goog.LOCALE == 'ky') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ky;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'ky_Cyrl' || goog.LOCALE == 'ky-Cyrl') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ky;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'ky_Cyrl_KG' || goog.LOCALE == 'ky-Cyrl-KG') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ky;
|
||||
}
|
||||
@@ -3861,6 +4178,10 @@ if (goog.LOCALE == 'mn') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_mn;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'mn_Cyrl' || goog.LOCALE == 'mn-Cyrl') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_mn;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'mn_Cyrl_MN' || goog.LOCALE == 'mn-Cyrl-MN') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_mn;
|
||||
}
|
||||
@@ -3877,6 +4198,10 @@ if (goog.LOCALE == 'ms') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ms;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'ms_Latn' || goog.LOCALE == 'ms-Latn') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ms;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'ms_Latn_MY' || goog.LOCALE == 'ms-Latn-MY') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_ms;
|
||||
}
|
||||
@@ -3945,6 +4270,10 @@ if (goog.LOCALE == 'pa') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_pa;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'pa_Guru' || goog.LOCALE == 'pa-Guru') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_pa;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'pa_Guru_IN' || goog.LOCALE == 'pa-Guru-IN') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_pa;
|
||||
}
|
||||
@@ -4021,10 +4350,22 @@ if (goog.LOCALE == 'sr') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_sr;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'sr_Cyrl' || goog.LOCALE == 'sr-Cyrl') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_sr;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'sr_Cyrl_RS' || goog.LOCALE == 'sr-Cyrl-RS') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_sr;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'sr_Latn' || goog.LOCALE == 'sr-Latn') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_sr_Latn;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'sr_Latn_RS' || goog.LOCALE == 'sr-Latn-RS') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_sr_Latn;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'sv') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_sv;
|
||||
}
|
||||
@@ -4097,6 +4438,10 @@ if (goog.LOCALE == 'uz') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_uz;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'uz_Latn' || goog.LOCALE == 'uz-Latn') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_uz;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'uz_Latn_UZ' || goog.LOCALE == 'uz-Latn-UZ') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_uz;
|
||||
}
|
||||
@@ -4121,6 +4466,10 @@ if (goog.LOCALE == 'zh_HK' || goog.LOCALE == 'zh-HK') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_zh_HK;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'zh_Hans' || goog.LOCALE == 'zh-Hans') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_zh;
|
||||
}
|
||||
|
||||
if (goog.LOCALE == 'zh_Hans_CN' || goog.LOCALE == 'zh-Hans-CN') {
|
||||
goog.i18n.NumberFormatSymbols = goog.i18n.NumberFormatSymbols_zh;
|
||||
}
|
||||
|
||||
+107
-1363
File diff suppressed because it is too large
Load Diff
@@ -17,7 +17,7 @@
|
||||
*
|
||||
* This file is autogenerated by script:
|
||||
* http://go/generate_pluralrules.py
|
||||
* File generated from CLDR ver. 26
|
||||
* File generated from CLDR ver. 27.0.1
|
||||
*
|
||||
* Before check in, this file could have been manually edited. This is to
|
||||
* incorporate changes before we could fix CLDR. All manual modification must be
|
||||
@@ -821,6 +821,9 @@ if (goog.LOCALE == 'ar') {
|
||||
if (goog.LOCALE == 'az') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.esSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'be') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.beSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'bg') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.esSelect_;
|
||||
}
|
||||
@@ -830,6 +833,9 @@ if (goog.LOCALE == 'bn') {
|
||||
if (goog.LOCALE == 'br') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.brSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'bs') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.srSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'ca') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.enSelect_;
|
||||
}
|
||||
@@ -863,6 +869,9 @@ if (goog.LOCALE == 'en') {
|
||||
if (goog.LOCALE == 'en_AU' || goog.LOCALE == 'en-AU') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.enSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'en_CA' || goog.LOCALE == 'en-CA') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.enSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'en_GB' || goog.LOCALE == 'en-GB') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.enSelect_;
|
||||
}
|
||||
@@ -890,6 +899,12 @@ if (goog.LOCALE == 'es_419' || goog.LOCALE == 'es-419') {
|
||||
if (goog.LOCALE == 'es_ES' || goog.LOCALE == 'es-ES') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.esSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'es_MX' || goog.LOCALE == 'es-MX') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.esSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'es_US' || goog.LOCALE == 'es-US') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.esSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'et') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.enSelect_;
|
||||
}
|
||||
@@ -1070,6 +1085,9 @@ if (goog.LOCALE == 'sq') {
|
||||
if (goog.LOCALE == 'sr') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.srSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'sr_Latn' || goog.LOCALE == 'sr-Latn') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.srSelect_;
|
||||
}
|
||||
if (goog.LOCALE == 'sv') {
|
||||
goog.i18n.pluralRules.select = goog.i18n.pluralRules.enSelect_;
|
||||
}
|
||||
|
||||
+1
-1
@@ -5,7 +5,7 @@ set -e
|
||||
BASE_DIR=`dirname $0`
|
||||
cd $BASE_DIR
|
||||
|
||||
./run-tests.sh
|
||||
npm run test-i18n
|
||||
|
||||
node src/closureSlurper.js
|
||||
|
||||
|
||||
@@ -1,6 +0,0 @@
|
||||
#!/bin/bash
|
||||
|
||||
set -e
|
||||
PARENT_DIR="$(dirname "$0")"
|
||||
|
||||
../node_modules/.bin/jasmine-node "$PARENT_DIR"/spec/
|
||||
@@ -4,6 +4,7 @@ findLocaleId = closureI18nExtractor.findLocaleId;
|
||||
extractNumberSymbols = closureI18nExtractor.extractNumberSymbols;
|
||||
extractCurrencySymbols = closureI18nExtractor.extractCurrencySymbols;
|
||||
extractDateTimeSymbols = closureI18nExtractor.extractDateTimeSymbols;
|
||||
outputLocale = closureI18nExtractor.outputLocale;
|
||||
|
||||
|
||||
function newTestLocaleInfo() {
|
||||
@@ -11,6 +12,8 @@ function newTestLocaleInfo() {
|
||||
DATETIME_FORMATS: {
|
||||
MONTH: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet', 'août', 'septembre',
|
||||
'octobre', 'novembre', 'décembre'],
|
||||
STANDALONEMONTH: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet', 'août', 'septembre',
|
||||
'octobre', 'novembre', 'décembre'],
|
||||
SHORTMONTH: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin', 'juil.', 'août', 'sept.', 'oct.',
|
||||
'nov.', 'déc.'],
|
||||
DAY: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi', 'samedi'],
|
||||
@@ -70,7 +73,7 @@ describe("findLocaleId", function() {
|
||||
it("should throw an error otherwise", function() {
|
||||
expect(function() {
|
||||
findLocaleId("str", "otherwise")
|
||||
}).toThrow("unknown type in findLocaleId: otherwise");
|
||||
}).toThrowError("unknown type in findLocaleId: otherwise");
|
||||
});
|
||||
});
|
||||
|
||||
@@ -129,7 +132,10 @@ describe("extractCurrencySymbols", function() {
|
||||
].join('\n');
|
||||
|
||||
var localeInfo = {};
|
||||
expect(extractCurrencySymbols(CONTENT)).toEqual({
|
||||
var currencySymbols = extractCurrencySymbols(CONTENT);
|
||||
expect(currencySymbols.GBP).toEqual([2, '£', 'GB£']);
|
||||
expect(currencySymbols.AOA).toEqual([2, 'Kz', 'Kz']);
|
||||
expect(currencySymbols).toEqual({
|
||||
'GBP':[2, '£', 'GB£'],
|
||||
'AOA':[2, 'Kz', 'Kz']
|
||||
});
|
||||
@@ -140,69 +146,71 @@ describe("extractCurrencySymbols", function() {
|
||||
describe("extractDateTimeSymbols", function() {
|
||||
it("should extract date time data", function() {
|
||||
var CONTENT = [
|
||||
"goog.i18n.DateTimeSymbols_fr_CA = {",
|
||||
" ERAS: ['av. J.-C.', 'ap. J.-C.'],",
|
||||
" ERANAMES: ['avant Jésus-Christ', 'après Jésus-Christ'],",
|
||||
" NARROWMONTHS: ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],",
|
||||
" STANDALONENARROWMONTHS: ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',",
|
||||
" 'N', 'D'],",
|
||||
" MONTHS: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet',",
|
||||
" 'août', 'septembre', 'octobre', 'novembre', 'décembre'],",
|
||||
" STANDALONEMONTHS: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin',",
|
||||
" 'juillet', 'août', 'septembre', 'octobre', 'novembre', 'décembre'],",
|
||||
" SHORTMONTHS: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin', 'juil.',",
|
||||
" 'août', 'sept.', 'oct.', 'nov.', 'déc.'],",
|
||||
" STANDALONESHORTMONTHS: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin',",
|
||||
" 'juil.', 'août', 'sept.', 'oct.', 'nov.', 'déc.'],",
|
||||
" WEEKDAYS: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi',",
|
||||
" 'samedi'],",
|
||||
" STANDALONEWEEKDAYS: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi',",
|
||||
" 'vendredi', 'samedi'],",
|
||||
" SHORTWEEKDAYS: ['dim.', 'lun.', 'mar.', 'mer.', 'jeu.', 'ven.', 'sam.'],",
|
||||
" STANDALONESHORTWEEKDAYS: ['dim.', 'lun.', 'mar.', 'mer.', 'jeu.', 'ven.',",
|
||||
" 'sam.'],",
|
||||
" NARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],",
|
||||
" STANDALONENARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],",
|
||||
" SHORTQUARTERS: ['T1', 'T2', 'T3', 'T4'],",
|
||||
" QUARTERS: ['1er trimestre', '2e trimestre', '3e trimestre', '4e trimestre'],",
|
||||
" AMPMS: ['AM', 'PM'],",
|
||||
" DATEFORMATS: ['EEEE d MMMM y', 'd MMMM y', 'yyyy-MM-dd', 'yy-MM-dd'],",
|
||||
" TIMEFORMATS: ['HH \\'h\\' mm \\'min\\' ss \\'s\\' zzzz', 'HH:mm:ss z',",
|
||||
" 'HH:mm:ss', 'HH:mm'],",
|
||||
" FIRSTDAYOFWEEK: 6,",
|
||||
" WEEKENDRANGE: [5, 6],",
|
||||
" FIRSTWEEKCUTOFFDAY: 2",
|
||||
"};"
|
||||
"goog.i18n.DateTimeSymbols_fr_CA = {",
|
||||
" ERAS: ['av. J.-C.', 'ap. J.-C.'],",
|
||||
" ERANAMES: ['avant Jésus-Christ', 'après Jésus-Christ'],",
|
||||
" NARROWMONTHS: ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O', 'N', 'D'],",
|
||||
" STANDALONENARROWMONTHS: ['J', 'F', 'M', 'A', 'M', 'J', 'J', 'A', 'S', 'O',",
|
||||
" 'N', 'D'],",
|
||||
" MONTHS: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet',",
|
||||
" 'août', 'septembre', 'octobre', 'novembre', 'décembre'],",
|
||||
" STANDALONEMONTHS: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin',",
|
||||
" 'juillet', 'août', 'septembre', 'octobre', 'novembre', 'décembre'],",
|
||||
" SHORTMONTHS: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin', 'juil.',",
|
||||
" 'août', 'sept.', 'oct.', 'nov.', 'déc.'],",
|
||||
" STANDALONESHORTMONTHS: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin',",
|
||||
" 'juil.', 'août', 'sept.', 'oct.', 'nov.', 'déc.'],",
|
||||
" WEEKDAYS: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi',",
|
||||
" 'samedi'],",
|
||||
" STANDALONEWEEKDAYS: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi',",
|
||||
" 'vendredi', 'samedi'],",
|
||||
" SHORTWEEKDAYS: ['dim.', 'lun.', 'mar.', 'mer.', 'jeu.', 'ven.', 'sam.'],",
|
||||
" STANDALONESHORTWEEKDAYS: ['dim.', 'lun.', 'mar.', 'mer.', 'jeu.', 'ven.',",
|
||||
" 'sam.'],",
|
||||
" NARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],",
|
||||
" STANDALONENARROWWEEKDAYS: ['D', 'L', 'M', 'M', 'J', 'V', 'S'],",
|
||||
" SHORTQUARTERS: ['T1', 'T2', 'T3', 'T4'],",
|
||||
" QUARTERS: ['1er trimestre', '2e trimestre', '3e trimestre', '4e trimestre'],",
|
||||
" AMPMS: ['AM', 'PM'],",
|
||||
" DATEFORMATS: ['EEEE d MMMM y', 'd MMMM y', 'yyyy-MM-dd', 'yy-MM-dd'],",
|
||||
" TIMEFORMATS: ['HH \\'h\\' mm \\'min\\' ss \\'s\\' zzzz', 'HH:mm:ss z',",
|
||||
" 'HH:mm:ss', 'HH:mm'],",
|
||||
" FIRSTDAYOFWEEK: 6,",
|
||||
" WEEKENDRANGE: [5, 6],",
|
||||
" FIRSTWEEKCUTOFFDAY: 2",
|
||||
"};"
|
||||
].join('\n');
|
||||
var localeInfo = {};
|
||||
var expectedLocaleInfo = {
|
||||
fr_CA: {
|
||||
DATETIME_FORMATS: {
|
||||
MONTH: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet', 'août', 'septembre',
|
||||
'octobre', 'novembre', 'décembre'],
|
||||
SHORTMONTH: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin', 'juil.', 'août', 'sept.', 'oct.',
|
||||
'nov.', 'déc.'],
|
||||
DAY: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi', 'samedi'],
|
||||
SHORTDAY: ['dim.', 'lun.', 'mar.', 'mer.', 'jeu.', 'ven.', 'sam.'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
ERAS: ['av. J.-C.', 'ap. J.-C.'],
|
||||
ERANAMES: ['avant Jésus-Christ', 'après Jésus-Christ'],
|
||||
medium: 'yyyy-MM-dd HH:mm:ss',
|
||||
short: 'yy-MM-dd HH:mm',
|
||||
fullDate: 'EEEE d MMMM y',
|
||||
longDate: 'd MMMM y',
|
||||
mediumDate: 'yyyy-MM-dd',
|
||||
shortDate: 'yy-MM-dd',
|
||||
mediumTime: 'HH:mm:ss',
|
||||
shortTime: 'HH:mm'
|
||||
}
|
||||
var localeInfo = {};
|
||||
var expectedLocaleInfo = {
|
||||
fr_CA: {
|
||||
DATETIME_FORMATS: {
|
||||
MONTH: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet', 'août', 'septembre',
|
||||
'octobre', 'novembre', 'décembre'],
|
||||
STANDALONEMONTH: ['janvier', 'février', 'mars', 'avril', 'mai', 'juin', 'juillet',
|
||||
'août', 'septembre', 'octobre', 'novembre', 'décembre'],
|
||||
SHORTMONTH: ['janv.', 'févr.', 'mars', 'avr.', 'mai', 'juin', 'juil.', 'août', 'sept.', 'oct.',
|
||||
'nov.', 'déc.'],
|
||||
DAY: ['dimanche', 'lundi', 'mardi', 'mercredi', 'jeudi', 'vendredi', 'samedi'],
|
||||
SHORTDAY: ['dim.', 'lun.', 'mar.', 'mer.', 'jeu.', 'ven.', 'sam.'],
|
||||
FIRSTDAYOFWEEK: 6,
|
||||
WEEKENDRANGE: [5, 6],
|
||||
AMPMS: ['AM', 'PM'],
|
||||
ERAS: ['av. J.-C.', 'ap. J.-C.'],
|
||||
ERANAMES: ['avant Jésus-Christ', 'après Jésus-Christ'],
|
||||
medium: 'yyyy-MM-dd HH:mm:ss',
|
||||
short: 'yy-MM-dd HH:mm',
|
||||
fullDate: 'EEEE d MMMM y',
|
||||
longDate: 'd MMMM y',
|
||||
mediumDate: 'yyyy-MM-dd',
|
||||
shortDate: 'yy-MM-dd',
|
||||
mediumTime: 'HH:mm:ss',
|
||||
shortTime: 'HH:mm'
|
||||
}
|
||||
};
|
||||
extractDateTimeSymbols(CONTENT, localeInfo);
|
||||
expect(localeInfo).toEqual(expectedLocaleInfo);
|
||||
})
|
||||
}
|
||||
};
|
||||
extractDateTimeSymbols(CONTENT, localeInfo);
|
||||
expect(localeInfo).toEqual(expectedLocaleInfo);
|
||||
});
|
||||
});
|
||||
|
||||
describe("pluralExtractor", function() {
|
||||
@@ -268,3 +276,10 @@ describe("serializeContent", function() {
|
||||
});
|
||||
});
|
||||
|
||||
describe("outputLocale", function() {
|
||||
it("should render the correct locale ids", function() {
|
||||
var output = outputLocale(newTestLocaleInfo(), 'fr_CA');
|
||||
expect(output).toContain('"id": "fr-ca"');
|
||||
expect(output).toContain('"localeID": "fr_CA"');
|
||||
});
|
||||
});
|
||||
|
||||
@@ -27,6 +27,7 @@ describe("convertNumberData", function() {
|
||||
describe("convertDatetimeData", function() {
|
||||
var convert = converter.convertDatetimeData,
|
||||
dataObj = { MONTHS: ['Enero', 'Pebrero'],
|
||||
STANDALONEMONTHS: ['Enero', 'Pebrero'],
|
||||
SHORTMONTHS: ['Ene', 'Peb'],
|
||||
WEEKDAYS: ['Linggo', 'Lunes'],
|
||||
SHORTWEEKDAYS: ['Lin', 'Lun'],
|
||||
@@ -37,6 +38,7 @@ describe("convertDatetimeData", function() {
|
||||
it('should convert empty datetime obj', function() {
|
||||
var processedData = convert(dataObj);
|
||||
expect(processedData.MONTH).toEqual(['Enero', 'Pebrero']);
|
||||
expect(processedData.STANDALONEMONTH).toEqual(['Enero', 'Pebrero']);
|
||||
expect(processedData.SHORTMONTH).toEqual(['Ene', 'Peb']);
|
||||
expect(processedData.DAY).toEqual(['Linggo', 'Lunes']);
|
||||
expect(processedData.SHORTDAY).toEqual(['Lin', 'Lun']);
|
||||
|
||||
@@ -38,16 +38,16 @@ describe('parsePattern', function() {
|
||||
parseAndExpect('#,##,##0.00\u00A4', '', '-', '\u00A4', '\u00A4', 1, 2, 2, 2, 3);
|
||||
parseAndExpect('#,##,##0.00\u00A4;(#,##,##0.00\u00A4)',
|
||||
'', '(', '\u00A4', '\u00A4)', 1, 2, 2, 2, 3);
|
||||
parseAndExpect('\u00A4#,##0.00', '\u00A4', '\u00A4-', '', '', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4#,##0.00', '\u00A4', '-\u00A4', '', '', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4#,##0.00;(\u00A4#,##0.00)',
|
||||
'\u00A4', '(\u00A4', '', ')', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4#,##0.00;\u00A4-#,##0.00',
|
||||
'\u00A4', '\u00A4-', '', '', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4 #,##0.00', '\u00A4 ', '\u00A4 -', '', '', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4 #,##0.00', '\u00A4 ', '-\u00A4 ', '', '', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4 #,##0.00;\u00A4-#,##0.00',
|
||||
'\u00A4 ', '\u00A4-', '', '', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4 #,##0.00;\u00A4 #,##0.00-',
|
||||
'\u00A4 ', '\u00A4 ', '', '-', 1, 2, 2, 3, 3);
|
||||
parseAndExpect('\u00A4 #,##,##0.00', '\u00A4 ', '\u00A4 -', '', '', 1, 2, 2, 2, 3);
|
||||
parseAndExpect('\u00A4 #,##,##0.00', '\u00A4 ', '-\u00A4 ', '', '', 1, 2, 2, 2, 3);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -50,10 +50,10 @@ function extractNumberSymbols(content, localeInfo, currencySymbols) {
|
||||
function extractCurrencySymbols(content) {
|
||||
//eval script in the current context so that we get access to all the symbols
|
||||
eval(content.toString());
|
||||
var currencySymbols = goog.i18n.currency.CurrencyInfo;
|
||||
currencySymbols.__proto__ = goog.i18n.currency.CurrencyInfoTier2;
|
||||
// var currencySymbols = goog.i18n.currency.CurrencyInfo;
|
||||
// currencySymbols.__proto__ = goog.i18n.currency.CurrencyInfoTier2;
|
||||
|
||||
return currencySymbols;
|
||||
return Object.assign({}, goog.i18n.currency.CurrencyInfoTier2, goog.i18n.currency.CurrencyInfo);
|
||||
}
|
||||
|
||||
function extractDateTimeSymbols(content, localeInfo) {
|
||||
@@ -79,7 +79,7 @@ function pluralExtractor(content, localeInfo) {
|
||||
goog.LOCALE = localeIds[i].match(/[^_]+/)[0];
|
||||
try {
|
||||
eval(contentText);
|
||||
} catch(e) {
|
||||
} catch (e) {
|
||||
console.log("Error in eval(contentText): " + e.stack);
|
||||
}
|
||||
if (!goog.i18n.pluralRules.select) {
|
||||
@@ -133,7 +133,7 @@ function canonicalizeForJsonStringify(unused_key, object) {
|
||||
|
||||
function serializeContent(localeObj) {
|
||||
return JSON.stringify(localeObj, canonicalizeForJsonStringify, ' ')
|
||||
.replace(new RegExp('[\\u007f-\\uffff]', 'g'), function(c) { return '\\u'+('0000'+c.charCodeAt(0).toString(16)).slice(-4); })
|
||||
.replace(new RegExp('[\\u007f-\\uffff]', 'g'), function(c) { return '\\u' + ('0000' + c.charCodeAt(0).toString(16)).slice(-4); })
|
||||
.replace(/"@@|@@"/g, '');
|
||||
}
|
||||
|
||||
@@ -161,6 +161,7 @@ function outputLocale(localeInfo, localeID) {
|
||||
if (!localeObj.DATETIME_FORMATS) {
|
||||
localeObj.DATETIME_FORMATS = fallBackObj.DATETIME_FORMATS;
|
||||
}
|
||||
localeObj.localeID = localeID;
|
||||
localeObj.id = correctedLocaleId(localeID);
|
||||
|
||||
var getDecimals = [
|
||||
@@ -201,10 +202,11 @@ function outputLocale(localeInfo, localeID) {
|
||||
DATETIME_FORMATS: localeObj.DATETIME_FORMATS,
|
||||
NUMBER_FORMATS: localeObj.NUMBER_FORMATS,
|
||||
pluralCat: localeObj.pluralCat,
|
||||
id: localeObj.id
|
||||
id: localeObj.id,
|
||||
localeID: localeID
|
||||
};
|
||||
|
||||
var content = serializeContent(localeInfo[localeID]);
|
||||
var content = serializeContent(localeObj);
|
||||
if (content.indexOf('getVF(') < 0) {
|
||||
getVF = '';
|
||||
}
|
||||
|
||||
@@ -39,6 +39,7 @@ function convertDatetimeData(dataObj) {
|
||||
|
||||
datetimeFormats.MONTH = dataObj.MONTHS;
|
||||
datetimeFormats.SHORTMONTH = dataObj.SHORTMONTHS;
|
||||
datetimeFormats.STANDALONEMONTH = dataObj.STANDALONEMONTHS;
|
||||
datetimeFormats.DAY = dataObj.WEEKDAYS;
|
||||
datetimeFormats.SHORTDAY = dataObj.SHORTWEEKDAYS;
|
||||
datetimeFormats.AMPMS = dataObj.AMPMS;
|
||||
|
||||
+2
-2
@@ -11,7 +11,7 @@ var PATTERN_SEP = ';',
|
||||
DIGIT = '#';
|
||||
|
||||
/**
|
||||
* main funciton for parser
|
||||
* main function for parser
|
||||
* @param str {string} pattern to be parsed (e.g. #,##0.###).
|
||||
*/
|
||||
function parsePattern(pattern) {
|
||||
@@ -56,7 +56,7 @@ function parsePattern(pattern) {
|
||||
p.negSuf = negative.substr(pos + trunkLen).replace(/\'/g, '');
|
||||
} else {
|
||||
// hardcoded '-' sign is fine as all locale use '-' as MINUS_SIGN. (\u2212 is the same as '-')
|
||||
p.negPre = p.posPre + '-';
|
||||
p.negPre = '-' + p.posPre;
|
||||
p.negSuf = p.posSuf;
|
||||
}
|
||||
|
||||
|
||||
@@ -2142,7 +2142,7 @@ queue}</string>
|
||||
\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qr
|
||||
|
||||
\f0\fs22 \cf2 $scope\
|
||||
name='Wold'}</string>
|
||||
name='World'}</string>
|
||||
<key>VerticalPad</key>
|
||||
<integer>0</integer>
|
||||
</dict>
|
||||
|
||||
@@ -17,7 +17,9 @@ module.exports = function(config, specificOptions) {
|
||||
testName: specificOptions.testName || 'AngularJS',
|
||||
startConnect: true,
|
||||
options: {
|
||||
'selenium-version': '2.41.0'
|
||||
// We need selenium version +2.46 for Firefox 39 and the last selenium version for OS X is 2.45.
|
||||
// TODO: Uncomment when there is a selenium 2.46 available for OS X.
|
||||
// 'selenium-version': '2.46.0'
|
||||
}
|
||||
},
|
||||
|
||||
@@ -35,12 +37,12 @@ module.exports = function(config, specificOptions) {
|
||||
'SL_Chrome': {
|
||||
base: 'SauceLabs',
|
||||
browserName: 'chrome',
|
||||
version: '39'
|
||||
version: '45'
|
||||
},
|
||||
'SL_Firefox': {
|
||||
base: 'SauceLabs',
|
||||
browserName: 'firefox',
|
||||
version: '31'
|
||||
version: '39'
|
||||
},
|
||||
'SL_Safari': {
|
||||
base: 'SauceLabs',
|
||||
|
||||
Executable
+8
@@ -0,0 +1,8 @@
|
||||
#!/bin/bash
|
||||
|
||||
set -e -o pipefail
|
||||
|
||||
|
||||
echo "Shutting down Browserstack tunnel"
|
||||
echo "TODO: implement me"
|
||||
exit 1
|
||||
+1
-1
@@ -116,7 +116,7 @@ module.exports = {
|
||||
.replace(/\\/g, '\\\\')
|
||||
.replace(/'/g, "\\'")
|
||||
.replace(/\r?\n/g, '\\n');
|
||||
js = "!window.angular.$$csp() && window.angular.element(document).find('head').prepend('<style type=\"text/css\">" + css + "</style>');";
|
||||
js = "!window.angular.$$csp().noInlineStyle && window.angular.element(document.head).prepend('<style type=\"text/css\">" + css + "</style>');";
|
||||
state.js.push(js);
|
||||
|
||||
return state;
|
||||
|
||||
@@ -0,0 +1,58 @@
|
||||
'use strict';
|
||||
|
||||
var path = require('path');
|
||||
var fs = require('fs');
|
||||
var glob = require("glob");
|
||||
var _ = require('lodash');
|
||||
var files = require('../../angularFiles').files;
|
||||
|
||||
module.exports = function(grunt) {
|
||||
|
||||
grunt.registerTask('validate-angular-files', function() {
|
||||
var combinedFiles = _.clone(files.angularModules);
|
||||
combinedFiles.ng = files.angularSrc;
|
||||
combinedFiles.angularLoader = files.angularLoader;
|
||||
|
||||
var errorsDetected = false;
|
||||
var directories = [];
|
||||
var detectedFiles = {};
|
||||
|
||||
for (var section in combinedFiles) {
|
||||
var sectionFiles = combinedFiles[section];
|
||||
|
||||
if (section != 'angularLoader') {
|
||||
directories.push('src/' + section);
|
||||
}
|
||||
|
||||
grunt.log.debug('Validating ' + sectionFiles.length + ' files from the "' + section + '" module.');
|
||||
|
||||
sectionFiles.forEach(function(file) {
|
||||
detectedFiles[file] = true;
|
||||
|
||||
if (!fs.existsSync(file)) {
|
||||
grunt.log.error(file + ' does not exist in the local file structure.');
|
||||
errorsDetected = true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
directories.forEach(function(directory) {
|
||||
glob.sync(directory + '/**/*').forEach(function(filePath) {
|
||||
if (!fs.lstatSync(filePath).isDirectory()) {
|
||||
var fileName = path.basename(filePath);
|
||||
var isHiddenFile = fileName[0] == '.';
|
||||
if (!isHiddenFile && !detectedFiles[filePath]) {
|
||||
grunt.log.error(filePath + ' exists in the local file structure but isn\'t used by any module.');
|
||||
errorsDetected = true;
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
if (errorsDetected) {
|
||||
throw new Error('Not all files were properly detected in the local file structure.');
|
||||
} else {
|
||||
grunt.log.ok('All files were detected successfully!');
|
||||
}
|
||||
});
|
||||
};
|
||||
@@ -1,309 +0,0 @@
|
||||
/*
|
||||
* HTML Parser By John Resig (ejohn.org)
|
||||
* Original code by Erik Arvidsson, Mozilla Public License
|
||||
* http://erik.eae.net/simplehtmlparser/simplehtmlparser.js
|
||||
*
|
||||
* // Use like so:
|
||||
* htmlParser(htmlString, {
|
||||
* start: function(tag, attrs, unary) {},
|
||||
* end: function(tag) {},
|
||||
* chars: function(text) {},
|
||||
* comment: function(text) {}
|
||||
* });
|
||||
*
|
||||
* // or to get an XML string:
|
||||
* HTMLtoXML(htmlString);
|
||||
*
|
||||
* // or to get an XML DOM Document
|
||||
* HTMLtoDOM(htmlString);
|
||||
*
|
||||
* // or to inject into an existing document/DOM node
|
||||
* HTMLtoDOM(htmlString, document);
|
||||
* HTMLtoDOM(htmlString, document.body);
|
||||
*
|
||||
*/
|
||||
|
||||
(function(){
|
||||
|
||||
// Regular Expressions for parsing tags and attributes
|
||||
var startTag = /^<(\w+)((?:\s+\w+(?:\s*=\s*(?:(?:"[^"]*")|(?:'[^']*')|[^>\s]+))?)*)\s*(\/?)>/,
|
||||
endTag = /^<\/(\w+)[^>]*>/,
|
||||
attr = /(\w+)(?:\s*=\s*(?:(?:"((?:\\.|[^"])*)")|(?:'((?:\\.|[^'])*)')|([^>\s]+)))?/g;
|
||||
|
||||
// Empty Elements - HTML 4.01
|
||||
var empty = makeMap("area,base,basefont,br,col,frame,hr,img,input,isindex,link,meta,param,embed");
|
||||
|
||||
// Block Elements - HTML 4.01
|
||||
var block = makeMap("address,applet,blockquote,button,center,dd,del,dir,div,dl,dt,fieldset,form,frameset,hr,iframe,ins,isindex,li,map,menu,noframes,noscript,object,ol,p,pre,script,table,tbody,td,tfoot,th,thead,tr,ul");
|
||||
|
||||
// Inline Elements - HTML 4.01
|
||||
var inline = makeMap("a,abbr,acronym,applet,b,basefont,bdo,big,br,button,cite,code,del,dfn,em,font,i,iframe,img,input,ins,kbd,label,map,object,q,s,samp,script,select,small,span,strike,strong,sub,sup,textarea,tt,u,var");
|
||||
|
||||
// Elements that you can, intentionally, leave open
|
||||
// (and which close themselves)
|
||||
var closeSelf = makeMap("colgroup,dd,dt,li,options,p,td,tfoot,th,thead,tr");
|
||||
|
||||
// Attributes that have their values filled in disabled="disabled"
|
||||
var fillAttrs = makeMap("checked,compact,declare,defer,disabled,ismap,multiple,nohref,noresize,noshade,nowrap,readonly,selected");
|
||||
|
||||
// Special Elements (can contain anything)
|
||||
var special = makeMap("script,style");
|
||||
|
||||
var htmlParser = this.htmlParser = function( html, handler ) {
|
||||
var index, chars, match, stack = [], last = html;
|
||||
stack.last = function(){
|
||||
return this[ this.length - 1 ];
|
||||
};
|
||||
|
||||
while ( html ) {
|
||||
chars = true;
|
||||
|
||||
// Make sure we're not in a script or style element
|
||||
if ( !stack.last() || !special[ stack.last() ] ) {
|
||||
|
||||
// Comment
|
||||
if ( html.indexOf("<!--") == 0 ) {
|
||||
index = html.indexOf("-->");
|
||||
|
||||
if ( index >= 0 ) {
|
||||
if ( handler.comment )
|
||||
handler.comment( html.substring( 4, index ) );
|
||||
html = html.substring( index + 3 );
|
||||
chars = false;
|
||||
}
|
||||
|
||||
// end tag
|
||||
} else if ( html.indexOf("</") == 0 ) {
|
||||
match = html.match( endTag );
|
||||
|
||||
if ( match ) {
|
||||
html = html.substring( match[0].length );
|
||||
match[0].replace( endTag, parseEndTag );
|
||||
chars = false;
|
||||
}
|
||||
|
||||
// start tag
|
||||
} else if ( html.indexOf("<") == 0 ) {
|
||||
match = html.match( startTag );
|
||||
|
||||
if ( match ) {
|
||||
html = html.substring( match[0].length );
|
||||
match[0].replace( startTag, parseStartTag );
|
||||
chars = false;
|
||||
}
|
||||
}
|
||||
|
||||
if ( chars ) {
|
||||
index = html.indexOf("<");
|
||||
|
||||
var text = index < 0 ? html : html.substring( 0, index );
|
||||
html = index < 0 ? "" : html.substring( index );
|
||||
|
||||
if ( handler.chars )
|
||||
handler.chars( text );
|
||||
}
|
||||
|
||||
} else {
|
||||
html = html.replace(new RegExp("(.*)<\/" + stack.last() + "[^>]*>"), function(all, text){
|
||||
text = text.replace(/<!--(.*?)-->/g, "$1")
|
||||
.replace(/<!\[CDATA\[(.*?)]]>/g, "$1");
|
||||
|
||||
if ( handler.chars )
|
||||
handler.chars( text );
|
||||
|
||||
return "";
|
||||
});
|
||||
|
||||
parseEndTag( "", stack.last() );
|
||||
}
|
||||
|
||||
if ( html == last )
|
||||
throw "Parse Error: " + html;
|
||||
last = html;
|
||||
}
|
||||
|
||||
// Clean up any remaining tags
|
||||
parseEndTag();
|
||||
|
||||
function parseStartTag( tag, tagName, rest, unary ) {
|
||||
if ( block[ tagName ] ) {
|
||||
while ( stack.last() && inline[ stack.last() ] ) {
|
||||
parseEndTag( "", stack.last() );
|
||||
}
|
||||
}
|
||||
|
||||
if ( closeSelf[ tagName ] && stack.last() == tagName ) {
|
||||
parseEndTag( "", tagName );
|
||||
}
|
||||
|
||||
unary = empty[ tagName ] || !!unary;
|
||||
|
||||
if ( !unary )
|
||||
stack.push( tagName );
|
||||
|
||||
if ( handler.start ) {
|
||||
var attrs = [];
|
||||
|
||||
rest.replace(attr, function(match, name) {
|
||||
var value = arguments[2] ? arguments[2] :
|
||||
arguments[3] ? arguments[3] :
|
||||
arguments[4] ? arguments[4] :
|
||||
fillAttrs[name] ? name : "";
|
||||
|
||||
attrs.push({
|
||||
name: name,
|
||||
value: value,
|
||||
escaped: value.replace(/(^|[^\\])"/g, '$1\\\"') //"
|
||||
});
|
||||
});
|
||||
|
||||
if ( handler.start )
|
||||
handler.start( tagName, attrs, unary );
|
||||
}
|
||||
}
|
||||
|
||||
function parseEndTag( tag, tagName ) {
|
||||
// If no tag name is provided, clean shop
|
||||
if ( !tagName )
|
||||
var pos = 0;
|
||||
|
||||
// Find the closest opened tag of the same type
|
||||
else
|
||||
for ( var pos = stack.length - 1; pos >= 0; pos-- )
|
||||
if ( stack[ pos ] == tagName )
|
||||
break;
|
||||
|
||||
if ( pos >= 0 ) {
|
||||
// Close all the open elements, up the stack
|
||||
for ( var i = stack.length - 1; i >= pos; i-- )
|
||||
if ( handler.end )
|
||||
handler.end( stack[ i ] );
|
||||
|
||||
// Remove the open elements from the stack
|
||||
stack.length = pos;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
this.HTMLtoXML = function( html ) {
|
||||
var results = "";
|
||||
|
||||
htmlParser(html, {
|
||||
start: function( tag, attrs, unary ) {
|
||||
results += "<" + tag;
|
||||
|
||||
for ( var i = 0; i < attrs.length; i++ )
|
||||
results += " " + attrs[i].name + '="' + attrs[i].escaped + '"';
|
||||
|
||||
results += (unary ? "/" : "") + ">";
|
||||
},
|
||||
end: function( tag ) {
|
||||
results += "</" + tag + ">";
|
||||
},
|
||||
chars: function( text ) {
|
||||
results += text;
|
||||
},
|
||||
comment: function( text ) {
|
||||
results += "<!--" + text + "-->";
|
||||
}
|
||||
});
|
||||
|
||||
return results;
|
||||
};
|
||||
|
||||
this.HTMLtoDOM = function( html, doc ) {
|
||||
// There can be only one of these elements
|
||||
var one = makeMap("html,head,body,title");
|
||||
|
||||
// Enforce a structure for the document
|
||||
var structure = {
|
||||
link: "head",
|
||||
base: "head"
|
||||
};
|
||||
|
||||
if ( !doc ) {
|
||||
if ( typeof DOMDocument != "undefined" )
|
||||
doc = new DOMDocument();
|
||||
else if ( typeof document != "undefined" && document.implementation && document.implementation.createDocument )
|
||||
doc = document.implementation.createDocument("", "", null);
|
||||
else if ( typeof ActiveX != "undefined" )
|
||||
doc = new ActiveXObject("Msxml.DOMDocument");
|
||||
|
||||
} else
|
||||
doc = doc.ownerDocument ||
|
||||
doc.getOwnerDocument && doc.getOwnerDocument() ||
|
||||
doc;
|
||||
|
||||
var elems = [],
|
||||
documentElement = doc.documentElement ||
|
||||
doc.getDocumentElement && doc.getDocumentElement();
|
||||
|
||||
// If we're dealing with an empty document then we
|
||||
// need to pre-populate it with the HTML document structure
|
||||
if ( !documentElement && doc.createElement ) (function(){
|
||||
var html = doc.createElement("html");
|
||||
var head = doc.createElement("head");
|
||||
head.appendChild( doc.createElement("title") );
|
||||
html.appendChild( head );
|
||||
html.appendChild( doc.createElement("body") );
|
||||
doc.appendChild( html );
|
||||
})();
|
||||
|
||||
// Find all the unique elements
|
||||
if ( doc.getElementsByTagName )
|
||||
for ( var i in one )
|
||||
one[ i ] = doc.getElementsByTagName( i )[0];
|
||||
|
||||
// If we're working with a document, inject contents into
|
||||
// the body element
|
||||
var curParentNode = one.body;
|
||||
|
||||
htmlParser( html, {
|
||||
start: function( tagName, attrs, unary ) {
|
||||
// If it's a pre-built element, then we can ignore
|
||||
// its construction
|
||||
if ( one[ tagName ] ) {
|
||||
curParentNode = one[ tagName ];
|
||||
return;
|
||||
}
|
||||
|
||||
var elem = doc.createElement( tagName );
|
||||
|
||||
for ( var attr in attrs )
|
||||
elem.setAttribute( attrs[ attr ].name, attrs[ attr ].value );
|
||||
|
||||
if ( structure[ tagName ] && typeof one[ structure[ tagName ] ] != "boolean" )
|
||||
one[ structure[ tagName ] ].appendChild( elem );
|
||||
|
||||
else if ( curParentNode && curParentNode.appendChild )
|
||||
curParentNode.appendChild( elem );
|
||||
|
||||
if ( !unary ) {
|
||||
elems.push( elem );
|
||||
curParentNode = elem;
|
||||
}
|
||||
},
|
||||
end: function( tag ) {
|
||||
elems.length -= 1;
|
||||
|
||||
// Init the new parentNode
|
||||
curParentNode = elems[ elems.length - 1 ];
|
||||
},
|
||||
chars: function( text ) {
|
||||
curParentNode.appendChild( doc.createTextNode( text ) );
|
||||
},
|
||||
comment: function( text ) {
|
||||
// create comment node
|
||||
}
|
||||
});
|
||||
|
||||
return doc;
|
||||
};
|
||||
|
||||
function makeMap(str){
|
||||
var obj = {}, items = str.split(",");
|
||||
for ( var i = 0; i < items.length; i++ )
|
||||
obj[ items[i] ] = true;
|
||||
return obj;
|
||||
}
|
||||
})();
|
||||
@@ -4,6 +4,8 @@
|
||||
var isFunction = function isFunction(value){return typeof value == 'function';};
|
||||
var isPromiseLike = function isPromiseLike(obj) {return obj && isFunction(obj.then);};
|
||||
var isObject = function isObject(value){return value != null && typeof value === 'object';};
|
||||
var isUndefined = function isUndefined(value) {return typeof value === 'undefined';};
|
||||
|
||||
var minErr = function minErr (module, constructor) {
|
||||
return function (){
|
||||
var ErrorConstructor = constructor || Error;
|
||||
@@ -11,6 +13,20 @@ var minErr = function minErr (module, constructor) {
|
||||
};
|
||||
};
|
||||
|
||||
var extend = function extend(dst) {
|
||||
for (var i = 1, ii = arguments.length; i < ii; i++) {
|
||||
var obj = arguments[i];
|
||||
if (obj) {
|
||||
var keys = Object.keys(obj);
|
||||
for (var j = 0, jj = keys.length; j < jj; j++) {
|
||||
var key = keys[j];
|
||||
dst[key] = obj[key];
|
||||
}
|
||||
}
|
||||
}
|
||||
return dst;
|
||||
};
|
||||
|
||||
var $q = qFactory(process.nextTick, function noopExceptionHandler() {});
|
||||
|
||||
exports.resolved = $q.resolve;
|
||||
|
||||
@@ -11,8 +11,7 @@ set -e
|
||||
# Curl and run this script as part of your .travis.yml before_script section:
|
||||
# before_script:
|
||||
# - curl https://gist.github.com/santiycr/5139565/raw/sauce_connect_setup.sh | bash
|
||||
|
||||
CONNECT_URL="https://saucelabs.com/downloads/sc-4.3.7-linux.tar.gz"
|
||||
CONNECT_URL="https://saucelabs.com/downloads/sc-4.3.13-linux.tar.gz"
|
||||
CONNECT_DIR="/tmp/sauce-connect-$RANDOM"
|
||||
CONNECT_DOWNLOAD="sc-4.3.7-linux.tar.gz"
|
||||
|
||||
|
||||
Executable
+16
@@ -0,0 +1,16 @@
|
||||
#!/bin/bash
|
||||
|
||||
set -e -o pipefail
|
||||
|
||||
|
||||
echo "Shutting down Sauce Connect tunnel"
|
||||
|
||||
killall sc
|
||||
|
||||
while [[ -n `ps -ef | grep "sauce-connect-" | grep -v "grep"` ]]; do
|
||||
printf "."
|
||||
sleep .5
|
||||
done
|
||||
|
||||
echo ""
|
||||
echo "Sauce Connect tunnel has been shut down"
|
||||
@@ -178,7 +178,7 @@ var getSnapshotVersion = function() {
|
||||
// last release was a non beta release. Increment the patch level to
|
||||
// indicate the next release that we will be doing.
|
||||
// E.g. last release was 1.3.0, then the snapshot will be
|
||||
// 1.3.1-build.1, which is lesser than 1.3.1 accorind the semver!
|
||||
// 1.3.1-build.1, which is lesser than 1.3.1 according to the semver!
|
||||
|
||||
// If the last release was a beta release we don't update the
|
||||
// beta number by purpose, as otherwise the semver comparison
|
||||
|
||||
+5258
-923
File diff suppressed because it is too large
Load Diff
Generated
+8306
-1599
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user