2 Copyright (c) 2003-2010, CKSource - Frederico Knabben. All rights reserved.
3 For licensing, see LICENSE.html or http://ckeditor.com/license
9 * It is possible to set things in three different places.
10 * 1. As attributes in the object tag.
11 * 2. As param tags under the object tag.
12 * 3. As attributes in the embed tag.
13 * It is possible for a single attribute to be present in more than one place.
14 * So let's define a mapping between a sementic attribute and its syntactic
16 * Then we'll set and retrieve attribute values according to the mapping,
17 * instead of having to check and set each syntactic attribute every time.
19 * Reference: http://kb.adobe.com/selfservice/viewContent.do?externalId=tn_12701
21 var ATTRTYPE_OBJECT
= 1,
27 id
: [ { type
: ATTRTYPE_OBJECT
, name
: 'id' } ],
28 classid
: [ { type
: ATTRTYPE_OBJECT
, name
: 'classid' } ],
29 codebase
: [ { type
: ATTRTYPE_OBJECT
, name
: 'codebase'} ],
30 pluginspage
: [ { type
: ATTRTYPE_EMBED
, name
: 'pluginspage' } ],
31 src
: [ { type
: ATTRTYPE_PARAM
, name
: 'movie' }, { type
: ATTRTYPE_EMBED
, name
: 'src' } ],
32 name
: [ { type
: ATTRTYPE_EMBED
, name
: 'name' } ],
33 align
: [ { type
: ATTRTYPE_OBJECT
, name
: 'align' } ],
34 title
: [ { type
: ATTRTYPE_OBJECT
, name
: 'title' }, { type
: ATTRTYPE_EMBED
, name
: 'title' } ],
35 'class' : [ { type
: ATTRTYPE_OBJECT
, name
: 'class' }, { type
: ATTRTYPE_EMBED
, name
: 'class'} ],
36 width
: [ { type
: ATTRTYPE_OBJECT
, name
: 'width' }, { type
: ATTRTYPE_EMBED
, name
: 'width' } ],
37 height
: [ { type
: ATTRTYPE_OBJECT
, name
: 'height' }, { type
: ATTRTYPE_EMBED
, name
: 'height' } ],
38 hSpace
: [ { type
: ATTRTYPE_OBJECT
, name
: 'hSpace' }, { type
: ATTRTYPE_EMBED
, name
: 'hSpace' } ],
39 vSpace
: [ { type
: ATTRTYPE_OBJECT
, name
: 'vSpace' }, { type
: ATTRTYPE_EMBED
, name
: 'vSpace' } ],
40 style
: [ { type
: ATTRTYPE_OBJECT
, name
: 'style' }, { type
: ATTRTYPE_EMBED
, name
: 'style' } ],
41 type
: [ { type
: ATTRTYPE_EMBED
, name
: 'type' } ]
44 var names
= [ 'play', 'loop', 'menu', 'quality', 'scale', 'salign', 'wmode', 'bgcolor', 'base', 'flashvars', 'allowScriptAccess',
46 for ( var i
= 0 ; i
< names
.length
; i
++ )
47 attributesMap
[ names
[i
] ] = [ { type
: ATTRTYPE_EMBED
, name
: names
[i
] }, { type
: ATTRTYPE_PARAM
, name
: names
[i
] } ];
48 names
= [ 'allowFullScreen', 'play', 'loop', 'menu' ];
49 for ( i
= 0 ; i
< names
.length
; i
++ )
50 attributesMap
[ names
[i
] ][0]['default'] = attributesMap
[ names
[i
] ][1]['default'] = true;
52 function loadValue( objectNode
, embedNode
, paramMap
)
54 var attributes
= attributesMap
[ this.id
];
58 var isCheckbox
= ( this instanceof CKEDITOR
.ui
.dialog
.checkbox
);
59 for ( var i
= 0 ; i
< attributes
.length
; i
++ )
61 var attrDef
= attributes
[ i
];
62 switch ( attrDef
.type
)
67 if ( objectNode
.getAttribute( attrDef
.name
) !== null )
69 var value
= objectNode
.getAttribute( attrDef
.name
);
71 this.setValue( value
.toLowerCase() == 'true' );
73 this.setValue( value
);
76 else if ( isCheckbox
)
77 this.setValue( !!attrDef
[ 'default' ] );
82 if ( attrDef
.name
in paramMap
)
84 value
= paramMap
[ attrDef
.name
];
86 this.setValue( value
.toLowerCase() == 'true' );
88 this.setValue( value
);
91 else if ( isCheckbox
)
92 this.setValue( !!attrDef
[ 'default' ] );
97 if ( embedNode
.getAttribute( attrDef
.name
) )
99 value
= embedNode
.getAttribute( attrDef
.name
);
101 this.setValue( value
.toLowerCase() == 'true' );
103 this.setValue( value
);
106 else if ( isCheckbox
)
107 this.setValue( !!attrDef
[ 'default' ] );
112 function commitValue( objectNode
, embedNode
, paramMap
)
114 var attributes
= attributesMap
[ this.id
];
118 var isRemove
= ( this.getValue() === '' ),
119 isCheckbox
= ( this instanceof CKEDITOR
.ui
.dialog
.checkbox
);
121 for ( var i
= 0 ; i
< attributes
.length
; i
++ )
123 var attrDef
= attributes
[i
];
124 switch ( attrDef
.type
)
126 case ATTRTYPE_OBJECT
:
129 var value
= this.getValue();
130 if ( isRemove
|| isCheckbox
&& value
=== attrDef
[ 'default' ] )
131 objectNode
.removeAttribute( attrDef
.name
);
133 objectNode
.setAttribute( attrDef
.name
, value
);
138 value
= this.getValue();
139 if ( isRemove
|| isCheckbox
&& value
=== attrDef
[ 'default' ] )
141 if ( attrDef
.name
in paramMap
)
142 paramMap
[ attrDef
.name
].remove();
146 if ( attrDef
.name
in paramMap
)
147 paramMap
[ attrDef
.name
].setAttribute( 'value', value
);
150 var param
= CKEDITOR
.dom
.element
.createFromHtml( '<cke:param></cke:param>', objectNode
.getDocument() );
151 param
.setAttributes( { name
: attrDef
.name
, value
: value
} );
152 if ( objectNode
.getChildCount() < 1 )
153 param
.appendTo( objectNode
);
155 param
.insertBefore( objectNode
.getFirst() );
162 value
= this.getValue();
163 if ( isRemove
|| isCheckbox
&& value
=== attrDef
[ 'default' ])
164 embedNode
.removeAttribute( attrDef
.name
);
166 embedNode
.setAttribute( attrDef
.name
, value
);
171 CKEDITOR
.dialog
.add( 'flash', function( editor
)
173 var makeObjectTag
= !editor
.config
.flashEmbedTagOnly
,
174 makeEmbedTag
= editor
.config
.flashAddEmbedTag
|| editor
.config
.flashEmbedTagOnly
;
176 var previewPreloader
,
177 previewAreaHtml
= '<div>' + CKEDITOR
.tools
.htmlEncode( editor
.lang
.common
.preview
) +'<br>' +
178 '<div id="FlashPreviewLoader" style="display:none"><div class="loading"> </div></div>' +
179 '<div id="FlashPreviewBox"></div></div>';
182 title
: editor
.lang
.flash
.title
,
187 // Clear previously saved elements.
188 this.fakeImage
= this.objectNode
= this.embedNode
= null;
189 previewPreloader
= new CKEDITOR
.dom
.element( 'embeded', editor
.document
);
191 // Try to detect any embed or object tag that has Flash parameters.
192 var fakeImage
= this.getSelectedElement();
193 if ( fakeImage
&& fakeImage
.getAttribute( '_cke_real_element_type' ) && fakeImage
.getAttribute( '_cke_real_element_type' ) == 'flash' )
195 this.fakeImage
= fakeImage
;
197 var realElement
= editor
.restoreRealElement( fakeImage
),
198 objectNode
= null, embedNode
= null, paramMap
= {};
199 if ( realElement
.getName() == 'cke:object' )
201 objectNode
= realElement
;
202 var embedList
= objectNode
.getElementsByTag( 'embed', 'cke' );
203 if ( embedList
.count() > 0 )
204 embedNode
= embedList
.getItem( 0 );
205 var paramList
= objectNode
.getElementsByTag( 'param', 'cke' );
206 for ( var i
= 0, length
= paramList
.count() ; i
< length
; i
++ )
208 var item
= paramList
.getItem( i
),
209 name
= item
.getAttribute( 'name' ),
210 value
= item
.getAttribute( 'value' );
211 paramMap
[ name
] = value
;
214 else if ( realElement
.getName() == 'cke:embed' )
215 embedNode
= realElement
;
217 this.objectNode
= objectNode
;
218 this.embedNode
= embedNode
;
220 this.setupContent( objectNode
, embedNode
, paramMap
, fakeImage
);
225 // If there's no selected object or embed, create one. Otherwise, reuse the
226 // selected object and embed nodes.
227 var objectNode
= null,
230 if ( !this.fakeImage
)
234 objectNode
= CKEDITOR
.dom
.element
.createFromHtml( '<cke:object></cke:object>', editor
.document
);
236 classid
: 'clsid:d27cdb6e-ae6d-11cf-96b8-444553540000',
237 codebase
: 'http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=6,0,40,0'
239 objectNode
.setAttributes( attributes
);
243 embedNode
= CKEDITOR
.dom
.element
.createFromHtml( '<cke:embed></cke:embed>', editor
.document
);
244 embedNode
.setAttributes(
246 type
: 'application/x-shockwave-flash',
247 pluginspage
: 'http://www.macromedia.com/go/getflashplayer'
250 embedNode
.appendTo( objectNode
);
255 objectNode
= this.objectNode
;
256 embedNode
= this.embedNode
;
259 // Produce the paramMap if there's an object tag.
263 var paramList
= objectNode
.getElementsByTag( 'param', 'cke' );
264 for ( var i
= 0, length
= paramList
.count() ; i
< length
; i
++ )
265 paramMap
[ paramList
.getItem( i
).getAttribute( 'name' ) ] = paramList
.getItem( i
);
268 // A subset of the specified attributes/styles
269 // should also be applied on the fake element to
270 // have better visual effect. (#5240)
271 var extraStyles
= {}, extraAttributes
= {};
272 this.commitContent( objectNode
, embedNode
, paramMap
, extraStyles
, extraAttributes
);
274 // Refresh the fake image.
275 var newFakeImage
= editor
.createFakeElement( objectNode
|| embedNode
, 'cke_flash', 'flash', true );
276 newFakeImage
.setAttributes( extraAttributes
);
277 newFakeImage
.setStyles( extraStyles
);
278 if ( this.fakeImage
)
280 newFakeImage
.replace( this.fakeImage
);
281 editor
.getSelection().selectElement( newFakeImage
);
284 editor
.insertElement( newFakeImage
);
290 this.preview
.setHtml('');
296 label
: editor
.lang
.common
.generalTab
,
307 widths
: [ '280px', '110px' ],
314 label
: editor
.lang
.common
.url
,
316 validate
: CKEDITOR
.dialog
.validate
.notEmpty( editor
.lang
.flash
.validateSrc
),
318 commit
: commitValue
,
321 var dialog
= this.getDialog(),
322 updatePreview = function( src
){
323 // Query the preloader to figure out the url impacted by based href.
324 previewPreloader
.setAttribute( 'src', src
);
325 dialog
.preview
.setHtml( '<embed height="100%" width="100%" src="'
326 + CKEDITOR
.tools
.htmlEncode( previewPreloader
.getAttribute( 'src' ) )
327 + '" type="application/x-shockwave-flash"></embed>' );
330 dialog
.preview
= dialog
.getContentElement( 'info', 'preview' ).getElement().getChild( 3 );
332 // Sync on inital value loaded.
333 this.on( 'change', function( evt
){
335 if ( evt
.data
&& evt
.data
.value
)
336 updatePreview( evt
.data
.value
);
338 // Sync when input value changed.
339 this.getInputElement().on( 'change', function( evt
){
341 updatePreview( this.getValue() );
348 filebrowser
: 'info:src',
350 // v-align with the 'src' field.
351 // TODO: We need something better than a fixed size here.
352 style
: 'display:inline-block;margin-top:10px;',
353 label
: editor
.lang
.common
.browseServer
361 widths
: [ '25%', '25%', '25%', '25%', '25%' ],
367 style
: 'width:95px',
368 label
: editor
.lang
.flash
.width
,
369 validate
: CKEDITOR
.dialog
.validate
.integer( editor
.lang
.flash
.validateWidth
),
370 setup : function( objectNode
, embedNode
, paramMap
, fakeImage
)
372 loadValue
.apply( this, arguments
);
375 var fakeImageWidth
= parseInt( fakeImage
.$.style
.width
, 10 );
376 if ( !isNaN( fakeImageWidth
) )
377 this.setValue( fakeImageWidth
);
380 commit : function( objectNode
, embedNode
, paramMap
, extraStyles
)
382 commitValue
.apply( this, arguments
);
383 if ( this.getValue() )
384 extraStyles
.width
= this.getValue() + 'px';
390 style
: 'width:95px',
391 label
: editor
.lang
.flash
.height
,
392 validate
: CKEDITOR
.dialog
.validate
.integer( editor
.lang
.flash
.validateHeight
),
393 setup : function( objectNode
, embedNode
, paramMap
, fakeImage
)
395 loadValue
.apply( this, arguments
);
398 var fakeImageHeight
= parseInt( fakeImage
.$.style
.height
, 10 );
399 if ( !isNaN( fakeImageHeight
) )
400 this.setValue( fakeImageHeight
);
403 commit : function( objectNode
, embedNode
, paramMap
, extraStyles
)
405 commitValue
.apply( this, arguments
);
406 if ( this.getValue() )
407 extraStyles
.height
= this.getValue() + 'px';
413 style
: 'width:95px',
414 label
: editor
.lang
.flash
.hSpace
,
415 validate
: CKEDITOR
.dialog
.validate
.integer( editor
.lang
.flash
.validateHSpace
),
422 style
: 'width:95px',
423 label
: editor
.lang
.flash
.vSpace
,
424 validate
: CKEDITOR
.dialog
.validate
.integer( editor
.lang
.flash
.validateVSpace
),
438 style
: 'width:95%;',
439 html
: previewAreaHtml
448 filebrowser
: 'uploadButton',
449 label
: editor
.lang
.common
.upload
,
455 label
: editor
.lang
.common
.upload
,
461 label
: editor
.lang
.common
.uploadSubmit
,
462 filebrowser
: 'info:src',
463 'for' : [ 'Upload', 'upload' ]
469 label
: editor
.lang
.flash
.propertiesTab
,
474 widths
: [ '50%', '50%' ],
480 label
: editor
.lang
.flash
.scale
,
482 style
: 'width : 100%;',
485 [ editor
.lang
.common
.notSet
, ''],
486 [ editor
.lang
.flash
.scaleAll
, 'showall' ],
487 [ editor
.lang
.flash
.scaleNoBorder
, 'noborder' ],
488 [ editor
.lang
.flash
.scaleFit
, 'exactfit' ]
494 id
: 'allowScriptAccess',
496 label
: editor
.lang
.flash
.access
,
498 style
: 'width : 100%;',
501 [ editor
.lang
.common
.notSet
, ''],
502 [ editor
.lang
.flash
.accessAlways
, 'always' ],
503 [ editor
.lang
.flash
.accessSameDomain
, 'samedomain' ],
504 [ editor
.lang
.flash
.accessNever
, 'never' ]
513 widths
: [ '50%', '50%' ],
519 label
: editor
.lang
.flash
.windowMode
,
521 style
: 'width : 100%;',
524 [ editor
.lang
.common
.notSet
, '' ],
525 [ editor
.lang
.flash
.windowModeWindow
, 'window' ],
526 [ editor
.lang
.flash
.windowModeOpaque
, 'opaque' ],
527 [ editor
.lang
.flash
.windowModeTransparent
, 'transparent' ]
535 label
: editor
.lang
.flash
.quality
,
537 style
: 'width : 100%;',
540 [ editor
.lang
.common
.notSet
, '' ],
541 [ editor
.lang
.flash
.qualityBest
, 'best' ],
542 [ editor
.lang
.flash
.qualityHigh
, 'high' ],
543 [ editor
.lang
.flash
.qualityAutoHigh
, 'autohigh' ],
544 [ editor
.lang
.flash
.qualityMedium
, 'medium' ],
545 [ editor
.lang
.flash
.qualityAutoLow
, 'autolow' ],
546 [ editor
.lang
.flash
.qualityLow
, 'low' ]
555 widths
: [ '50%', '50%' ],
561 label
: editor
.lang
.flash
.align
,
563 style
: 'width : 100%;',
566 [ editor
.lang
.common
.notSet
, ''],
567 [ editor
.lang
.flash
.alignLeft
, 'left'],
568 [ editor
.lang
.flash
.alignAbsBottom
, 'absBottom'],
569 [ editor
.lang
.flash
.alignAbsMiddle
, 'absMiddle'],
570 [ editor
.lang
.flash
.alignBaseline
, 'baseline'],
571 [ editor
.lang
.flash
.alignBottom
, 'bottom'],
572 [ editor
.lang
.flash
.alignMiddle
, 'middle'],
573 [ editor
.lang
.flash
.alignRight
, 'right'],
574 [ editor
.lang
.flash
.alignTextTop
, 'textTop'],
575 [ editor
.lang
.flash
.alignTop
, 'top']
578 commit : function( objectNode
, embedNode
, paramMap
, extraStyles
, extraAttributes
)
580 var value
= this.getValue();
581 commitValue
.apply( this, arguments
);
582 value
&& ( extraAttributes
.align
= value
);
593 label
: CKEDITOR
.tools
.htmlEncode( editor
.lang
.flash
.flashvars
),
604 label
: editor
.lang
.flash
.chkMenu
,
612 label
: editor
.lang
.flash
.chkPlay
,
620 label
: editor
.lang
.flash
.chkLoop
,
627 id
: 'allowFullScreen',
628 label
: editor
.lang
.flash
.chkFull
,
641 label
: editor
.lang
.common
.advancedTab
,
646 widths
: [ '45%', '55%' ],
652 label
: editor
.lang
.common
.id
,
659 label
: editor
.lang
.common
.advisoryTitle
,
667 widths
: [ '45%', '55%' ],
673 label
: editor
.lang
.flash
.bgcolor
,
680 label
: editor
.lang
.common
.cssClass
,
689 label
: editor
.lang
.common
.cssStyle
,