styles.js 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454
  1. /**
  2. * @license Copyright (c) 2003-2019, CKSource - Frederico Knabben. All rights reserved.
  3. * For licensing, see LICENSE.md or https://ckeditor.com/legal/ckeditor-oss-license
  4. */
  5. import StyleProxy from '../../src/view/styles';
  6. describe( 'Styles', () => {
  7. let styleProxy;
  8. beforeEach( () => {
  9. styleProxy = new StyleProxy();
  10. } );
  11. describe( 'styles rules', () => {
  12. describe( 'border', () => {
  13. it( 'should parse border shorthand', () => {
  14. styleProxy.setStyle( 'border:1px solid blue;' );
  15. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  16. top: { color: 'blue', style: 'solid', width: '1px' },
  17. right: { color: 'blue', style: 'solid', width: '1px' },
  18. bottom: { color: 'blue', style: 'solid', width: '1px' },
  19. left: { color: 'blue', style: 'solid', width: '1px' }
  20. } );
  21. } );
  22. it( 'should parse border shorthand with other shorthands', () => {
  23. styleProxy.setStyle( 'border:1px solid blue;border-left:#665511 dashed 2.7em;border-top:7px dotted #ccc;' );
  24. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  25. top: { color: '#ccc', style: 'dotted', width: '7px' },
  26. right: { color: 'blue', style: 'solid', width: '1px' },
  27. bottom: { color: 'blue', style: 'solid', width: '1px' },
  28. left: { color: '#665511', style: 'dashed', width: '2.7em' }
  29. } );
  30. } );
  31. it( 'should output inline shorthand rules', () => {
  32. styleProxy.setStyle( 'border:1px solid blue;' );
  33. expect( styleProxy.getInlineStyle() ).to.equal( 'border:1px solid blue;' );
  34. expect( styleProxy.getInlineRule( 'border' ) ).to.equal( '1px solid blue' );
  35. expect( styleProxy.getInlineRule( 'border-top' ) ).to.equal( '1px solid blue' );
  36. expect( styleProxy.getInlineRule( 'border-right' ) ).to.equal( '1px solid blue' );
  37. expect( styleProxy.getInlineRule( 'border-bottom' ) ).to.equal( '1px solid blue' );
  38. expect( styleProxy.getInlineRule( 'border-left' ) ).to.equal( '1px solid blue' );
  39. } );
  40. it( 'should output inline shorthand rules', () => {
  41. styleProxy.setStyle( 'border:1px solid blue;border-left:#665511 dashed 2.7em;border-top:7px dotted #ccc;' );
  42. expect( styleProxy.getInlineStyle() ).to.equal(
  43. 'border-top:7px dotted #ccc;border-right:1px solid blue;border-bottom:1px solid blue;border-left:2.7em dashed #665511;'
  44. );
  45. expect( styleProxy.getInlineRule( 'border' ) ).to.be.undefined;
  46. expect( styleProxy.getInlineRule( 'border-top' ) ).to.equal( '7px dotted #ccc' );
  47. expect( styleProxy.getInlineRule( 'border-right' ) ).to.equal( '1px solid blue' );
  48. expect( styleProxy.getInlineRule( 'border-bottom' ) ).to.equal( '1px solid blue' );
  49. expect( styleProxy.getInlineRule( 'border-left' ) ).to.equal( '2.7em dashed #665511' );
  50. } );
  51. it( 'should merge rules on insert other shorthand', () => {
  52. styleProxy.setStyle( 'border:1px solid blue;' );
  53. styleProxy.insertRule( 'border-left', '#665511 dashed 2.7em' );
  54. styleProxy.insertRule( 'border-top', '7px dotted #ccc' );
  55. expect( styleProxy.getInlineStyle() ).to.equal(
  56. 'border-top:7px dotted #ccc;border-right:1px solid blue;border-bottom:1px solid blue;border-left:2.7em dashed #665511;'
  57. );
  58. expect( styleProxy.getInlineRule( 'border' ) ).to.be.undefined;
  59. expect( styleProxy.getInlineRule( 'border-top' ) ).to.equal( '7px dotted #ccc' );
  60. expect( styleProxy.getInlineRule( 'border-right' ) ).to.equal( '1px solid blue' );
  61. expect( styleProxy.getInlineRule( 'border-bottom' ) ).to.equal( '1px solid blue' );
  62. expect( styleProxy.getInlineRule( 'border-left' ) ).to.equal( '2.7em dashed #665511' );
  63. } );
  64. it( 'should output', () => {
  65. styleProxy.setStyle( 'border:1px solid blue;' );
  66. styleProxy.removeRule( 'border-top' );
  67. expect( styleProxy.getInlineStyle() ).to.equal(
  68. 'border-right:1px solid blue;border-bottom:1px solid blue;border-left:1px solid blue;'
  69. );
  70. expect( styleProxy.getInlineRule( 'border' ) ).to.be.undefined;
  71. expect( styleProxy.getInlineRule( 'border-top' ) ).to.be.undefined;
  72. expect( styleProxy.getInlineRule( 'border-right' ) ).to.equal( '1px solid blue' );
  73. expect( styleProxy.getInlineRule( 'border-bottom' ) ).to.equal( '1px solid blue' );
  74. expect( styleProxy.getInlineRule( 'border-left' ) ).to.equal( '1px solid blue' );
  75. } );
  76. describe( 'border-color', () => {
  77. it( 'should set all border colors (1 value defined)', () => {
  78. styleProxy.setStyle( 'border-color:cyan;' );
  79. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  80. top: { color: 'cyan' },
  81. left: { color: 'cyan' },
  82. bottom: { color: 'cyan' },
  83. right: { color: 'cyan' }
  84. } );
  85. } );
  86. it( 'should set all border colors (2 values defined)', () => {
  87. styleProxy.setStyle( 'border-color:cyan magenta;' );
  88. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  89. top: { color: 'cyan' },
  90. right: { color: 'magenta' },
  91. bottom: { color: 'cyan' },
  92. left: { color: 'magenta' }
  93. } );
  94. } );
  95. it( 'should set all border colors (3 values defined)', () => {
  96. styleProxy.setStyle( 'border-color:cyan magenta pink;' );
  97. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  98. top: { color: 'cyan' },
  99. right: { color: 'magenta' },
  100. bottom: { color: 'pink' },
  101. left: { color: 'magenta' }
  102. } );
  103. } );
  104. it( 'should set all border colors (4 values defined)', () => {
  105. styleProxy.setStyle( 'border-color:cyan magenta pink beige;' );
  106. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  107. top: { color: 'cyan' },
  108. right: { color: 'magenta' },
  109. bottom: { color: 'pink' },
  110. left: { color: 'beige' }
  111. } );
  112. } );
  113. it( 'should merge with border shorthand', () => {
  114. styleProxy.setStyle( 'border:1px solid blue;border-color:cyan black;' );
  115. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  116. top: { color: 'cyan', style: 'solid', width: '1px' },
  117. right: { color: 'black', style: 'solid', width: '1px' },
  118. bottom: { color: 'cyan', style: 'solid', width: '1px' },
  119. left: { color: 'black', style: 'solid', width: '1px' }
  120. } );
  121. } );
  122. } );
  123. describe( 'border-style', () => {
  124. it( 'should set all border styles (1 value defined)', () => {
  125. styleProxy.setStyle( 'border-style:solid;' );
  126. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  127. top: { style: 'solid' },
  128. right: { style: 'solid' },
  129. bottom: { style: 'solid' },
  130. left: { style: 'solid' }
  131. } );
  132. } );
  133. it( 'should set all border styles (2 values defined)', () => {
  134. styleProxy.setStyle( 'border-style:solid dotted;' );
  135. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  136. top: { style: 'solid' },
  137. right: { style: 'dotted' },
  138. bottom: { style: 'solid' },
  139. left: { style: 'dotted' }
  140. } );
  141. } );
  142. it( 'should set all border styles (3 values defined)', () => {
  143. styleProxy.setStyle( 'border-style:solid dotted dashed;' );
  144. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  145. top: { style: 'solid' },
  146. right: { style: 'dotted' },
  147. bottom: { style: 'dashed' },
  148. left: { style: 'dotted' }
  149. } );
  150. } );
  151. it( 'should set all border styles (4 values defined)', () => {
  152. styleProxy.setStyle( 'border-style:solid dotted dashed ridge;' );
  153. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  154. top: { style: 'solid' },
  155. right: { style: 'dotted' },
  156. bottom: { style: 'dashed' },
  157. left: { style: 'ridge' }
  158. } );
  159. } );
  160. } );
  161. describe( 'border-width', () => {
  162. it( 'should set all border widths (1 value defined)', () => {
  163. styleProxy.setStyle( 'border-width:1px;' );
  164. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  165. top: { width: '1px' },
  166. right: { width: '1px' },
  167. bottom: { width: '1px' },
  168. left: { width: '1px' }
  169. } );
  170. } );
  171. it( 'should set all border widths (2 values defined)', () => {
  172. styleProxy.setStyle( 'border-width:1px .34cm;' );
  173. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  174. top: { width: '1px' },
  175. right: { width: '.34cm' },
  176. bottom: { width: '1px' },
  177. left: { width: '.34cm' }
  178. } );
  179. } );
  180. it( 'should set all border widths (3 values defined)', () => {
  181. styleProxy.setStyle( 'border-width:1px .34cm 90.1rem;' );
  182. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  183. top: { width: '1px' },
  184. right: { width: '.34cm' },
  185. bottom: { width: '90.1rem' },
  186. left: { width: '.34cm' }
  187. } );
  188. } );
  189. it( 'should set all border widths (4 values defined)', () => {
  190. styleProxy.setStyle( 'border-width:1px .34cm 90.1rem thick;' );
  191. expect( styleProxy.getModel( 'border' ) ).to.deep.equal( {
  192. top: { width: '1px' },
  193. right: { width: '.34cm' },
  194. bottom: { width: '90.1rem' },
  195. left: { width: 'thick' }
  196. } );
  197. } );
  198. } );
  199. } );
  200. describe( 'margin', () => {
  201. it( 'should set all margins (1 value defined)', () => {
  202. styleProxy.setStyle( 'margin:1px;' );
  203. expect( styleProxy.getModel( 'margin' ) ).to.deep.equal( {
  204. top: '1px',
  205. right: '1px',
  206. bottom: '1px',
  207. left: '1px'
  208. } );
  209. } );
  210. it( 'should set all margins (2 values defined)', () => {
  211. styleProxy.setStyle( 'margin:1px .34cm;' );
  212. expect( styleProxy.getModel( 'margin' ) ).to.deep.equal( {
  213. top: '1px',
  214. right: '.34cm',
  215. bottom: '1px',
  216. left: '.34cm'
  217. } );
  218. } );
  219. it( 'should set all margins (3 values defined)', () => {
  220. styleProxy.setStyle( 'margin:1px .34cm 90.1rem;' );
  221. expect( styleProxy.getModel( 'margin' ) ).to.deep.equal( {
  222. top: '1px',
  223. right: '.34cm',
  224. bottom: '90.1rem',
  225. left: '.34cm'
  226. } );
  227. } );
  228. it( 'should set all margins (4 values defined)', () => {
  229. styleProxy.setStyle( 'margin:1px .34cm 90.1rem thick;' );
  230. expect( styleProxy.getModel( 'margin' ) ).to.deep.equal( {
  231. top: '1px',
  232. right: '.34cm',
  233. bottom: '90.1rem',
  234. left: 'thick'
  235. } );
  236. } );
  237. it( 'should output inline style (1 value defined)', () => {
  238. styleProxy.setStyle( 'margin:1px;' );
  239. expect( styleProxy.getInlineStyle() ).to.equal( 'margin:1px;' );
  240. expect( styleProxy.getInlineRule( 'margin' ) ).to.equal( '1px' );
  241. expect( styleProxy.getInlineRule( 'margin-top' ) ).to.equal( '1px' );
  242. expect( styleProxy.getInlineRule( 'margin-right' ) ).to.equal( '1px' );
  243. expect( styleProxy.getInlineRule( 'margin-bottom' ) ).to.equal( '1px' );
  244. expect( styleProxy.getInlineRule( 'margin-left' ) ).to.equal( '1px' );
  245. } );
  246. it( 'should output inline style (2 values defined)', () => {
  247. styleProxy.setStyle( 'margin:1px .34cm;' );
  248. expect( styleProxy.getInlineStyle() ).to.equal( 'margin:1px .34cm;' );
  249. expect( styleProxy.getInlineRule( 'margin' ) ).to.equal( '1px .34cm' );
  250. expect( styleProxy.getInlineRule( 'margin-top' ) ).to.equal( '1px' );
  251. expect( styleProxy.getInlineRule( 'margin-right' ) ).to.equal( '.34cm' );
  252. expect( styleProxy.getInlineRule( 'margin-bottom' ) ).to.equal( '1px' );
  253. expect( styleProxy.getInlineRule( 'margin-left' ) ).to.equal( '.34cm' );
  254. } );
  255. it( 'should output inline style (3 values defined)', () => {
  256. styleProxy.setStyle( 'margin:1px .34cm 90.1rem;' );
  257. expect( styleProxy.getInlineStyle() ).to.equal( 'margin:1px .34cm 90.1rem;' );
  258. expect( styleProxy.getInlineRule( 'margin' ) ).to.equal( '1px .34cm 90.1rem' );
  259. expect( styleProxy.getInlineRule( 'margin-top' ) ).to.equal( '1px' );
  260. expect( styleProxy.getInlineRule( 'margin-right' ) ).to.equal( '.34cm' );
  261. expect( styleProxy.getInlineRule( 'margin-bottom' ) ).to.equal( '90.1rem' );
  262. expect( styleProxy.getInlineRule( 'margin-left' ) ).to.equal( '.34cm' );
  263. } );
  264. it( 'should output inline style (3 values defined, only last different)', () => {
  265. styleProxy.setStyle( 'margin:1px 1px 90.1rem;' );
  266. expect( styleProxy.getInlineStyle() ).to.equal( 'margin:1px 1px 90.1rem;' );
  267. expect( styleProxy.getInlineRule( 'margin' ) ).to.equal( '1px 1px 90.1rem' );
  268. expect( styleProxy.getInlineRule( 'margin-top' ) ).to.equal( '1px' );
  269. expect( styleProxy.getInlineRule( 'margin-right' ) ).to.equal( '1px' );
  270. expect( styleProxy.getInlineRule( 'margin-bottom' ) ).to.equal( '90.1rem' );
  271. expect( styleProxy.getInlineRule( 'margin-left' ) ).to.equal( '1px' );
  272. } );
  273. it( 'should output inline style (4 values defined)', () => {
  274. styleProxy.setStyle( 'margin:1px .34cm 90.1rem thick;' );
  275. expect( styleProxy.getInlineStyle() ).to.equal( 'margin:1px .34cm 90.1rem thick;' );
  276. expect( styleProxy.getInlineRule( 'margin' ) ).to.equal( '1px .34cm 90.1rem thick' );
  277. expect( styleProxy.getInlineRule( 'margin-top' ) ).to.equal( '1px' );
  278. expect( styleProxy.getInlineRule( 'margin-right' ) ).to.equal( '.34cm' );
  279. expect( styleProxy.getInlineRule( 'margin-bottom' ) ).to.equal( '90.1rem' );
  280. expect( styleProxy.getInlineRule( 'margin-left' ) ).to.equal( 'thick' );
  281. } );
  282. it( 'should output inline style (4 values defined, only last different)', () => {
  283. styleProxy.setStyle( 'margin:1px 1px 1px thick;' );
  284. expect( styleProxy.getInlineStyle() ).to.equal( 'margin:1px 1px 1px thick;' );
  285. expect( styleProxy.getInlineRule( 'margin' ) ).to.equal( '1px 1px 1px thick' );
  286. expect( styleProxy.getInlineRule( 'margin-top' ) ).to.equal( '1px' );
  287. expect( styleProxy.getInlineRule( 'margin-right' ) ).to.equal( '1px' );
  288. expect( styleProxy.getInlineRule( 'margin-bottom' ) ).to.equal( '1px' );
  289. expect( styleProxy.getInlineRule( 'margin-left' ) ).to.equal( 'thick' );
  290. } );
  291. describe( 'margin-*', () => {
  292. it( 'should set proper margin', () => {
  293. styleProxy.setStyle( 'margin-top:1px;' );
  294. expect( styleProxy.getModel( 'margin' ) ).to.deep.equal( { top: '1px' } );
  295. expect( styleProxy.getModel( 'margin-top' ) ).to.equal( '1px' );
  296. } );
  297. it( 'should set proper margin with margin shorthand', () => {
  298. styleProxy.setStyle( 'margin: 2em;margin-top:1px;' );
  299. expect( styleProxy.getModel( 'margin' ) ).to.deep.equal( {
  300. top: '1px',
  301. right: '2em',
  302. bottom: '2em',
  303. left: '2em'
  304. } );
  305. expect( styleProxy.getModel( 'margin-top' ) ).to.equal( '1px' );
  306. expect( styleProxy.getModel( 'margin-right' ) ).to.equal( '2em' );
  307. expect( styleProxy.getModel( 'margin-bottom' ) ).to.equal( '2em' );
  308. expect( styleProxy.getModel( 'margin-left' ) ).to.equal( '2em' );
  309. } );
  310. } );
  311. } );
  312. describe( 'padding', () => {
  313. it( 'should set all paddings (1 value defined)', () => {
  314. styleProxy.setStyle( 'padding:1px;' );
  315. expect( styleProxy.getModel( 'padding' ) ).to.deep.equal( {
  316. top: '1px',
  317. right: '1px',
  318. bottom: '1px',
  319. left: '1px'
  320. } );
  321. } );
  322. it( 'should set all paddings (2 values defined)', () => {
  323. styleProxy.setStyle( 'padding:1px .34cm;' );
  324. expect( styleProxy.getModel( 'padding' ) ).to.deep.equal( {
  325. top: '1px',
  326. right: '.34cm',
  327. bottom: '1px',
  328. left: '.34cm'
  329. } );
  330. } );
  331. it( 'should set all paddings (3 values defined)', () => {
  332. styleProxy.setStyle( 'padding:1px .34cm 90.1rem;' );
  333. expect( styleProxy.getModel( 'padding' ) ).to.deep.equal( {
  334. top: '1px',
  335. right: '.34cm',
  336. bottom: '90.1rem',
  337. left: '.34cm'
  338. } );
  339. } );
  340. it( 'should set all paddings (4 values defined)', () => {
  341. styleProxy.setStyle( 'padding:1px .34cm 90.1rem thick;' );
  342. expect( styleProxy.getModel( 'padding' ) ).to.deep.equal( {
  343. top: '1px',
  344. right: '.34cm',
  345. bottom: '90.1rem',
  346. left: 'thick'
  347. } );
  348. } );
  349. describe( 'padding-*', () => {
  350. it( 'should set proper padding', () => {
  351. styleProxy.setStyle( 'padding-top:1px;' );
  352. expect( styleProxy.getModel( 'padding' ) ).to.deep.equal( {
  353. top: '1px'
  354. } );
  355. } );
  356. it( 'should set proper padding with padding shorthand', () => {
  357. styleProxy.setStyle( 'padding: 2em;padding-top:1px;' );
  358. expect( styleProxy.getModel( 'padding' ) ).to.deep.equal( {
  359. top: '1px',
  360. right: '2em',
  361. bottom: '2em',
  362. left: '2em'
  363. } );
  364. } );
  365. } );
  366. } );
  367. describe( 'unknown rules', () => {
  368. it( 'should left rules untouched', () => {
  369. styleProxy.setStyle( 'foo-bar:baz 1px abc;baz: 2px 3em;' );
  370. expect( styleProxy.getInlineStyle() ).to.equal( 'baz:2px 3em;foo-bar:baz 1px abc;' );
  371. expect( styleProxy.getInlineRule( 'foo-bar' ) ).to.equal( 'baz 1px abc' );
  372. expect( styleProxy.getInlineRule( 'baz' ) ).to.equal( '2px 3em' );
  373. } );
  374. } );
  375. } );
  376. } );