1/*jslint white: true, onevar: true, undef: true, nomen: true, eqeqeq: true, plusplus: true, bitwise: true, regexp: false, strict: true, newcap: true, immed: true */ 2/*global jQuery, window, DOKU_BASE*/ 3"use strict"; 4 5// TODO 6// * fix the css to have pointers on the +/- images in the tree when JS is enabled 7// * fix the css to have pointers on a.select when JS is enabled 8// * remame all the variables starting with $ once the port is over 9 10/** 11 * JavaScript functionalitiy for the media management popup 12 * 13 * @author Andreas Gohr <andi@splitbrain.org> 14 * @author Pierre Spring <pierre.spring@caillou.ch> 15 */ 16(function ($) { 17 var toggle, list, prepare_content, insert, confirmattach, attachoptions, initpopup; 18 19 /** 20 * build the popup window 21 * 22 * @author Dominik Eckelmann <eckelmann@cosmocode.de> 23 */ 24 initpopup = function() { 25 var popup; 26 27 popup = document.createElement('div'); 28 popup.setAttribute('id','media__popup'); 29 30 var root = document.getElementById('media__manager'); 31 if (root == null) return; 32 root.appendChild(popup); 33 34 var headline = document.createElement('h1'); 35 headline.innerHTML = LANG.mediatitle; 36 var headlineimg = document.createElement('img'); 37 headlineimg.src = DOKU_BASE + 'lib/images/close.png'; 38 headlineimg.id = 'media__closeimg'; 39 $(headlineimg).click(function () {$(popup).hide()}); 40 headline.insertBefore(headlineimg, headline.firstChild); 41 popup.appendChild(headline); 42 drag.attach(popup,headline); // Pierre: TODO 43 44 // link 45 46 var linkp = document.createElement('p'); 47 48 linkp.id = "media__linkstyle"; 49 if (media_manager.display == "2") { 50 linkp.style.display = "none"; 51 } 52 53 var linkl = document.createElement('label'); 54 linkl.innerHTML = LANG.mediatarget; 55 linkp.appendChild(linkl); 56 57 var linkbtns = ['lnk', 'direct', 'nolnk', 'displaylnk']; 58 for (var i = 0 ; i < linkbtns.length ; ++i) { 59 var linkbtn = document.createElement('button'); 60 linkbtn.className = 'button'; 61 linkbtn.value = i + 1; 62 linkbtn.id = "media__linkbtn" + (i + 1); 63 linkbtn.title = LANG['media' + linkbtns[i]]; 64 linkbtn.style.borderStyle = 'outset'; 65 $(linkbtn).click(function (event) { return media_manager.setlink(event,this); }); 66 67 var linkimg = document.createElement('img'); 68 linkimg.src = DOKU_BASE + 'lib/images/media_link_' + linkbtns[i] + '.png'; 69 70 linkbtn.appendChild(linkimg); 71 linkp.appendChild(linkbtn); 72 } 73 74 popup.appendChild(linkp); 75 76 // align 77 78 var alignp = document.createElement('p'); 79 var alignl = document.createElement('label'); 80 81 alignp.appendChild(alignl); 82 alignp.id = 'media__align'; 83 if (media_manager.display == "2") { 84 alignp.style.display = "none"; 85 } 86 alignl.innerHTML = LANG['mediaalign']; 87 88 var alignbtns = ['noalign', 'left', 'center', 'right']; 89 for (var n = 0 ; n < alignbtns.length ; ++n) { 90 var alignbtn = document.createElement('button'); 91 var alignimg = document.createElement('img'); 92 alignimg.src = DOKU_BASE + 'lib/images/media_align_' + alignbtns[n] + '.png'; 93 94 alignbtn.id = "media__alignbtn" + n; 95 alignbtn.value = n; 96 alignbtn.title = LANG['media' + alignbtns[n]]; 97 alignbtn.className = 'button'; 98 alignbtn.appendChild(alignimg); 99 alignbtn.style.borderStyle = 'outset'; 100 $(alignbtn).click(function (event) { return media_manager.setalign(event,this); }); 101 102 alignp.appendChild(alignbtn); 103 } 104 105 popup.appendChild(alignp); 106 107 // size 108 109 var sizep = document.createElement('p'); 110 var sizel = document.createElement('label'); 111 112 sizep.id = 'media__size'; 113 if (media_manager.display == "2") { 114 sizep.style.display = "none"; 115 } 116 sizep.appendChild(sizel); 117 sizel.innerHTML = LANG['mediasize']; 118 119 var sizebtns = ['small', 'medium', 'large', 'original']; 120 for (var size = 0 ; size < sizebtns.length ; ++size) { 121 var sizebtn = document.createElement('button'); 122 var sizeimg = document.createElement('img'); 123 124 sizep.appendChild(sizebtn); 125 sizeimg.src = DOKU_BASE + 'lib/images/media_size_' + sizebtns[size] + '.png'; 126 127 sizebtn.className = 'button'; 128 sizebtn.appendChild(sizeimg); 129 sizebtn.value = size + 1; 130 sizebtn.id = 'media__sizebtn' + (size + 1); 131 sizebtn.title = LANG['media' + sizebtns[size]]; 132 sizebtn.style.borderStyle = 'outset'; 133 $(sizebtn).click(function (event) { return media_manager.setsize(event,this); }); 134 } 135 136 popup.appendChild(sizep); 137 138 // send and close button 139 140 var btnp = document.createElement('p'); 141 popup.appendChild(btnp); 142 btnp.setAttribute('class','btnlbl'); 143 144 var cls = document.createElement('input'); 145 cls.type = 'button'; 146 cls.setAttribute('class','button'); 147 cls.value = LANG['mediaclose']; 148 btnp.appendChild(cls); 149 150 $(cls).click(function () {$(popup).hide();}); 151 152 var btn = document.createElement('input'); 153 btn.type = 'button'; 154 btn.id = 'media__sendbtn'; 155 btn.setAttribute('class','button'); 156 btn.value = LANG['mediainsert']; 157 btnp.appendChild(btn); 158 }; 159 160 /** 161 * Insert the clicked image into the opener's textarea 162 * 163 * @author Andreas Gohr <andi@splitbrain.org> 164 * @author Dominik Eckelmann <eckelmann@cosmocode.de> 165 * @author Pierre Spring <pierre.spring@caillou.ch> 166 */ 167 insert = function (id) { 168 var opts, optsstart, alignleft, alignright; 169 170 // set syntax options 171 $('#media__popup').hide(); 172 173 opts = ''; 174 optsstart = ''; 175 alignleft = ''; 176 alignright = ''; 177 178 if (media_manager.ext == 'img' || media_manager.ext == 'swf') { 179 180 if (media_manager.link == '4') { 181 opts = '?linkonly'; 182 } else { 183 184 if (media_manager.link == "3" && media_manager.ext == 'img') { 185 opts = '?nolink'; 186 optsstart = true; 187 } else if (media_manager.link == "2" && media_manager.ext == 'img') { 188 opts = '?direct'; 189 optsstart = true; 190 } 191 192 var s = parseInt(media_manager.size); 193 194 if (s && s >= 1) { 195 opts += (optsstart)?'&':'?'; 196 if (s=="1") { 197 opts += '100'; 198 if (media_manager.ext == 'swf') { 199 opts += 'x62'; 200 } 201 } else if (s=="2") { 202 opts += '200'; 203 if (media_manager.ext == 'swf') { 204 opts += 'x123'; 205 } 206 } else if (s=="3"){ 207 opts += '300'; 208 if (media_manager.ext == 'swf') { 209 opts += 'x185'; 210 } 211 } 212 } 213 if (media_manager.align == '1') { 214 alignleft = ''; 215 alignright = ' '; 216 } 217 if (media_manager.align == '2') { 218 alignleft = ' '; 219 alignright = ' '; 220 } 221 if (media_manager.align == '3') { 222 alignleft = ' '; 223 alignright = ''; 224 } 225 } 226 } 227 opener.insertTags('wiki__text','{{'+alignleft+id+opts+alignright+'|','}}',''); 228 229 if(!media_manager.keepopen) window.close(); 230 opener.focus(); 231 return false; 232 }; 233 234 /** 235 * Prefills the wikiname. 236 * 237 * @author Andreas Gohr <andi@splitbrain.org> 238 */ 239 suggest = function(){ 240 var file, name, text; 241 242 file = $(this); 243 name = $('#upload__name'); 244 if(!file.size() || !name.size()) return; 245 246 text = file.val(); 247 text = text.substr(text.lastIndexOf('/')+1); 248 text = text.substr(text.lastIndexOf('\\')+1); 249 name.val(text); 250 }; 251 252 /** 253 * Open or close a subtree using AJAX 254 * 255 * @author Andreas Gohr <andi@splitbrain.org> 256 * @author Pierre Spring <pierre.spring@caillou.ch> 257 */ 258 toggle = function (event) { 259 var clicky, listitem, sublist, link, ul; 260 261 event.preventDefault(); // TODO: really here? 262 263 var clicky = $(this); 264 var listitem = clicky.parent(); 265 266 // if already open, close by removing the sublist 267 sublist = listitem.find('ul').first(); 268 if(sublist.size()){ 269 sublist.remove(); // TODO: really? we could just hide it, right? 270 clicky.attr('src', DOKU_BASE + 'lib/images/plus.gif'); 271 return; 272 } 273 274 // get the enclosed link (is always the first one) 275 link = listitem.find('a').first(); 276 277 //prepare the new ul 278 ul = $('<ul/>'); 279 280 //fixme add classname here 281 282 $.post( 283 DOKU_BASE + 'lib/exe/ajax.php', 284 link.attr('search').substr(1) + '&call=medians', 285 function (data) { 286 ul.html(data) 287 listitem.append(ul); 288 }, 289 'html' 290 ); 291 292 clicky.attr('src', DOKU_BASE + 'lib/images/minus.gif'); 293 }; 294 295 /** 296 * list the content of a namespace using AJAX 297 * 298 * @author Andreas Gohr <andi@splitbrain.org> 299 * @author Pierre Spring <pierre.spring@caillou.ch> 300 */ 301 list = function (event) { 302 var link, content; 303 link = $(this); 304 305 event.preventDefault(); 306 307 cleanMsgArea(); 308 content = $('#media__content'); 309 content.html('<img src="' + DOKU_BASE + 'lib/images/loading.gif" alt="..." class="load" />'); 310 311 // fetch the subtree 312 $.post( 313 DOKU_BASE + 'lib/exe/ajax.php', 314 link.attr('search').substr(1)+'&call=medialist', 315 function (data) { 316 content.html(data); 317 prepare_content(content); 318 media_manager.updatehide(); 319 }, 320 'html' 321 ); 322 323 }; 324 325 prepare_content = function (content) { 326 // hide syntax example 327 content.find('div.example:visible').hide(); 328 initFlashUpload(); 329 }; 330 331 /** 332 * shows the popup for a image link 333 */ 334 select = function(event){ 335 var link, id, dot, ext; 336 337 event.preventDefault(); 338 339 link = $(this); 340 id = link.attr('name').substr(2); 341 342 if(!opener){ 343 // if we don't run in popup display example 344 // the id's are a bit wired and $('#ex_wiki_dokuwiki-128.png') will not be found 345 // by Sizzle (the CSS Selector Engine used by jQuery), 346 // hence the document.getElementById() call 347 $(document.getElementById('ex_'+id.replace(/:/g,'_').replace(/^_/,''))).toggle(); 348 return; 349 } 350 351 link = link[0]; 352 353 media_manager.ext = false; 354 dot = id.lastIndexOf("."); 355 356 if (-1 === dot) { 357 insert(id); 358 return; 359 } 360 361 ext = id.substr(dot); 362 363 if (ext != '.jpg' && ext != '.jpeg' && ext != '.png' && ext != '.gif' && ext != '.swf') { 364 insert(id); 365 return; 366 } 367 368 // remove old callback from the insert button and set the new one. 369 $('#media__sendbtn').unbind().click(function () {insert(id)}); 370 371 $('#media__popup').show() 372 .css('left', event.pageX + 'px') 373 .css('top', event.pageY + 'px'); 374 375 $('#media__popup button.button').each(function (index, element) { media_manager.outSet(element) } ); 376 377 378 if (ext == '.swf') { 379 media_manager.ext = 'swf'; 380 381 // disable display buttons for detail and linked image 382 $('#media__linkbtn1').hide(); 383 $('#media__linkbtn2').hide(); 384 385 // set the link button to default 386 if (media_manager.link != false) { 387 if ( media_manager.link == '2' || media_manager.link == '1') { 388 media_manager.inSet('media__linkbtn3'); 389 media_manager.link = '3'; 390 DokuCookie.setValue('link','3'); 391 } else { 392 media_manager.inSet('media__linkbtn'+media_manager.link); 393 } 394 } else if (DokuCookie.getValue('link')) { 395 if ( DokuCookie.getValue('link') == '2' || DokuCookie.getValue('link') == '1') { 396 // this options are not availible 397 media_manager.inSet('media__linkbtn3'); 398 media_manager.link = '3'; 399 DokuCookie.setValue('link','3'); 400 } else { 401 media_manager.inSet('media__linkbtn'+DokuCookie.getValue('link')); 402 media_manager.link = DokuCookie.getValue('link'); 403 } 404 } else { 405 // default case 406 media_manager.link = '3'; 407 media_manager.inSet('media__linkbtn3'); 408 DokuCookie.setValue('link','3'); 409 } 410 411 // disable button for original size 412 $('#media__sizebtn4').hide(); 413 414 } else { 415 media_manager.ext = 'img'; 416 417 // ensure that the display buttons are there 418 $('#media__linkbtn1').show(); 419 $('#media__linkbtn2').show(); 420 $('#media__sizebtn4').show(); 421 422 // set the link button to default 423 if (DokuCookie.getValue('link')) { 424 media_manager.link = DokuCookie.getValue('link'); 425 } 426 if (media_manager.link == false) { 427 // default case 428 media_manager.link = '1'; 429 DokuCookie.setValue('link','1'); 430 } 431 media_manager.inSet('media__linkbtn'+media_manager.link); 432 } 433 434 if (media_manager.link == '4') { 435 media_manager.align = false; 436 media_manager.size = false; 437 $('#media__align').hide(); 438 $('#media__size').hide(); 439 } else { 440 $('#media__align').show(); 441 $('#media__size').show(); 442 443 // set the align button to default 444 if (media_manager.align != false) { 445 media_manager.inSet('media__alignbtn'+media_manager.align); 446 } else if (DokuCookie.getValue('align')) { 447 media_manager.inSet('media__alignbtn'+DokuCookie.getValue('align')); 448 media_manager.align = DokuCookie.getValue('align'); 449 } else { 450 // default case 451 media_manager.align = '0'; 452 media_manager.inSet('media__alignbtn0'); 453 DokuCookie.setValue('align','0'); 454 } 455 456 // set the size button to default 457 if (DokuCookie.getValue('size')) { 458 media_manager.size = DokuCookie.getValue('size'); 459 } 460 if (media_manager.size == false || (media_manager.size === '4' && ext === '.swf')) { 461 // default case 462 media_manager.size = '2'; 463 DokuCookie.setValue('size','2'); 464 } 465 media_manager.inSet('media__sizebtn'+media_manager.size); 466 467 $('#media__sendbtn').focus(); 468 } 469 470 return; 471 }; 472 473 /** 474 * Deletion confirmation dialog to the delete buttons. 475 * 476 * @author Michael Klier <chi@chimeric.de> 477 * @author Pierre Spring <pierre.spring@caillou.ch> 478 */ 479 confirmattach = function(e){ 480 if(!confirm(LANG['del_confirm'] + "\n" + jQuery(this).attr('title'))) { 481 e.preventDefault(); 482 } 483 }; 484 485 /** 486 * Creates checkboxes for additional options 487 * 488 * @author Andreas Gohr <andi@splitbrain.org> 489 * @author Pierre Spring <pierre.spring@caillou.ch> 490 */ 491 attachoptions = function(){ 492 obj = $('#media__opts')[0] 493 if(!obj) return; 494 495 // keep open 496 if(opener){ 497 var kobox = document.createElement('input'); 498 kobox.type = 'checkbox'; 499 kobox.id = 'media__keepopen'; 500 if(DokuCookie.getValue('keepopen')){ 501 kobox.checked = true; 502 kobox.defaultChecked = true; //IE wants this 503 media_manager.keepopen = true; 504 } 505 506 $(kobox).click( 507 function () { 508 toggleOption(this, 'keepopen'); 509 } 510 ); 511 512 var kolbl = document.createElement('label'); 513 kolbl.htmlFor = 'media__keepopen'; 514 kolbl.innerHTML = LANG['keepopen']; 515 516 var kobr = document.createElement('br'); 517 518 obj.appendChild(kobox); 519 obj.appendChild(kolbl); 520 obj.appendChild(kobr); 521 } 522 523 // hide details 524 var hdbox = document.createElement('input'); 525 hdbox.type = 'checkbox'; 526 hdbox.id = 'media__hide'; 527 if(DokuCookie.getValue('hide')){ 528 hdbox.checked = true; 529 hdbox.defaultChecked = true; //IE wants this 530 media_manager.hide = true; 531 } 532 $(hdbox).click( 533 function () { 534 toggleOption(this, 'hide'); 535 media_manager.updatehide(); 536 } 537 ); 538 539 var hdlbl = document.createElement('label'); 540 hdlbl.htmlFor = 'media__hide'; 541 hdlbl.innerHTML = LANG['hidedetails']; 542 543 var hdbr = document.createElement('br'); 544 545 obj.appendChild(hdbox); 546 obj.appendChild(hdlbl); 547 obj.appendChild(hdbr); 548 media_manager.updatehide(); 549 }, 550 551 /** 552 * Generalized toggler 553 * 554 * @author Pierre Spring <pierre.spring@caillou.ch> 555 */ 556 toggleOption = function (checkbox, variable) { 557 if (checkbox.checked) { 558 DokuCookie.setValue(variable, 1); 559 media_manager[variable] = true; 560 } else { 561 DokuCookie.setValue(variable, ''); 562 media_manager[variable] = false; 563 } 564 } 565 566 initFlashUpload = function () { 567 var oform, oflash, title; 568 if(!hasFlash(8)) return; 569 570 oform = $('#dw__upload'); 571 oflash = $('#dw__flashupload'); 572 573 if(!oform.size() || !oflash.size()) return; 574 575 title = LANG['mu_btn']; 576 577 $('<img/>').attr('src', DOKU_BASE+'lib/images/multiupload.png') 578 .attr('title', title) 579 .attr('alt', title) 580 .css('cursor', 'pointer') 581 .click( 582 function () { 583 oform.hide(); 584 oflash.show(); 585 } 586 ) 587 .appendTo(oform); 588 }; 589 590 $(function () { 591 var content = $('#media__content'); 592 prepare_content(content); 593 594 attachoptions(); 595 initpopup(); 596 597 // add the action to autofill the "upload as" field 598 content.delegate('#upload__file', 'change', suggest) 599 // Attach the image selector action to all links 600 .delegate('a.select', 'click', select) 601 // Attach deletion confirmation dialog to the delete buttons 602 .delegate('#media__content a.btn_media_delete', 'click', confirmattach); 603 604 605 $('#media__tree').delegate('img', 'click', toggle) 606 .delegate('a', 'click', list); 607 }); 608}(jQuery)); 609 610var media_manager = { 611 keepopen: false, 612 hide: false, 613 align: false, 614 popup: false, 615 display: false, 616 link: false, 617 size: false, 618 ext: false, 619 620 /** 621 * Sets the visibility of the image details accordingly to the 622 * chosen hide state 623 * 624 * @author Andreas Gohr <andi@splitbrain.org> 625 */ 626 updatehide: function(){ 627 var obj = $('media__content'); 628 if(!obj) return; 629 var details = getElementsByClass('detail',obj,'div'); 630 for(var i=0; i<details.length; i++){ 631 if(media_manager.hide){ 632 details[i].style.display = 'none'; 633 }else{ 634 details[i].style.display = ''; 635 } 636 } 637 }, 638 639 /** 640 * set the align 641 * 642 * @author Dominik Eckelmann <eckelmann@cosmocode.de> 643 */ 644 setalign: function(event,cb){ 645 if(cb.value){ 646 DokuCookie.setValue('align',cb.value); 647 media_manager.align = cb.value; 648 media_manager.outSet("media__alignbtn0"); 649 media_manager.outSet("media__alignbtn1"); 650 media_manager.outSet("media__alignbtn2"); 651 media_manager.outSet("media__alignbtn3"); 652 media_manager.inSet("media__alignbtn"+cb.value); 653 }else{ 654 DokuCookie.setValue('align',''); 655 media_manager.align = false; 656 } 657 }, 658 /** 659 * set the link type 660 * 661 * @author Dominik Eckelmann <eckelmann@cosmocode.de> 662 */ 663 setlink: function(event,cb){ 664 if(cb.value){ 665 DokuCookie.setValue('link',cb.value); 666 media_manager.link = cb.value; 667 media_manager.outSet("media__linkbtn1"); 668 media_manager.outSet("media__linkbtn2"); 669 media_manager.outSet("media__linkbtn3"); 670 media_manager.outSet("media__linkbtn4"); 671 media_manager.inSet("media__linkbtn"+cb.value); 672 var size = document.getElementById("media__size"); 673 var align = document.getElementById("media__align"); 674 if (cb.value != '4') { 675 size.style.display = "block"; 676 align.style.display = "block"; 677 } else { 678 size.style.display = "none"; 679 align.style.display = "none"; 680 } 681 }else{ 682 DokuCookie.setValue('link',''); 683 media_manager.link = false; 684 } 685 }, 686 687 /** 688 * set the display type 689 * 690 * @author Dominik Eckelmann <eckelmann@cosmocode.de> 691 */ 692 setdisplay: function(event,cb){ 693 if(cb.value){ 694 DokuCookie.setValue('display',cb.value); 695 media_manager.display = cb.value; 696 media_manager.outSet("media__displaybtn1"); 697 media_manager.outSet("media__displaybtn2"); 698 media_manager.inSet("media__displaybtn"+cb.value); 699 700 }else{ 701 DokuCookie.setValue('display',''); 702 media_manager.align = false; 703 } 704 }, 705 706 /** 707 * sets the border to outset 708 */ 709 outSet: function(element) { 710 if ('string' === typeof element) { 711 element = '#' + element; 712 } 713 jQuery(element).css('border-style', 'outset'); 714 }, 715 716 /** 717 * sets the border to inset 718 */ 719 inSet: function(id) { 720 var ele = document.getElementById(id); 721 if (ele == null) return; 722 ele.style.borderStyle = "inset"; 723 }, 724 725 /** 726 * set the image size 727 * 728 * @author Dominik Eckelmann <eckelmann@cosmocode.de> 729 */ 730 setsize: function(event,cb){ 731 if (cb.value) { 732 DokuCookie.setValue('size',cb.value); 733 media_manager.size = cb.value; 734 for (var i = 1 ; i <= 4 ; ++i) { 735 media_manager.outSet("media__sizebtn" + i); 736 } 737 media_manager.inSet("media__sizebtn"+cb.value); 738 } else { 739 DokuCookie.setValue('size',''); 740 media_manager.width = false; 741 } 742 } 743};