source: trunk/spip/esqueleto-redcta/plugins/crayons/js/crayons.js @ 69

Last change on this file since 69 was 69, checked in by guille, 16 years ago

Se agrego Plugin Crayon y se actualizaron los esqueletos para que funcione

File size: 12.8 KB
Line 
1(function($){
2/*
3 *  crayons.js (c) Fil, toggg 2006-2007 -- licence GPL
4 */
5
6// le prototype configuration de Crayons
7$.prototype.cfgCrayons = function (options) {
8  this.url_crayons_html = options['dir_racine']+'spip.php?action=crayons_html';
9  this.img = {
10    'searching':{'txt':'En attente du serveur ...'},
11    'edit':{'txt':'Editer'},
12    'img-changed':{'txt':'Deja modifie'}
13  };
14  this.txt = {
15  };
16  for (opt in options) {
17    this[opt] = options[opt];
18  }
19};
20
21$.prototype.cfgCrayons.prototype.mkimg = function(what, extra) {
22  return '<em class="crayon-'+what+'" title="'+ this.img[what].txt + (extra ? extra : '') + '"></em>';
23/*  return '<img class="crayon-' + what +
24    '" src="' + this.imgPath + '/' + this.img[what].file +
25    '" title="' + this.img[what].txt + (extra ? extra : '') + ' /">';
26*/
27};
28
29$.prototype.cfgCrayons.prototype.iconclick = function(c) {
30
31  // le + qui passe en prive pour editer tout si classe type--id
32  var link = c.match(/\b(\w+)--(\d+)\b/);
33  link = link ? 
34    '<a href="ecrire/?exec=' + link[1] + 's_edit&id_' + link[1] + '=' + link[2] +
35    '">' + this.mkimg('edit', ' (' + link[1] + ' ' + link[2] + ')') + '</a>' : '';
36
37  var cray = c.match(/\b\w+-(\w+)-\d+\b/);
38  var boite = !cray ? '' : this.mkimg('crayon', ' (' + cray[1] + ')');
39
40  return "<span class='crayon-icones'><span>" + boite +
41      this.mkimg('img-changed', cray ? ' (' + cray[1] + ')': '') +
42      link +"</span></span>";
43};
44
45function entity2unicode(txt)
46{
47  var reg = txt.split(/&#(\d+);/i);
48  for (var i = 1; i < reg.length; i+=2) {
49    reg[i] = String.fromCharCode(parseInt(reg[i]));
50  }
51  return reg.join('');
52};
53
54function uniAlert(txt)
55{
56  alert(entity2unicode(txt));
57};
58
59function uniConfirm(txt)
60{
61  return confirm(entity2unicode(txt));
62};
63
64// donne le crayon d'un element
65$.fn.crayon = function(){
66  if (this.length)
67    return $(
68      $.map(this, function(a){
69        return '#'+($(a).find('.crayon-icones').attr('rel'));
70      })
71      .join(','));
72  else
73    return $([]);
74};
75
76// ouvre un crayon
77$.fn.opencrayon = function(evt, percent) {
78  if (evt && evt.stopPropagation) {
79    evt.stopPropagation();
80  }
81  return this
82  .each(function(){
83    // verifier que je suis un crayon
84    if (!$(this).is('.crayon'))
85      return;
86
87    // voir si je dispose deja du crayon comme voisin
88    if ($(this).is('.crayon-has')) {
89      $(this)
90      .css('visibility','hidden')
91      .crayon()
92        .show();
93    }
94    // sinon charger le formulaire
95    else {
96      // sauf si je suis deja en train de le charger (lock)
97      if ($(this).find("em.crayon-searching").length) {
98        return;
99      }
100      $(this)
101      .find('>span.crayon-icones span')
102      .append(configCrayons.mkimg('searching')); // icone d'attente
103      var me=this;
104      var params = {
105        'w': $(this).width(),
106        'h': $(this).height(),
107        'wh': window.innerHeight,
108        'em': $(this).px('fontSize'), // eviter un bug MSIE sur fontSize
109        'class': me.className,
110        'color': $(this).css('color'),
111        'font-size': $(this).px('fontSize'),
112        'font-family': $(this).css('fontFamily'),
113        'font-weight': $(this).css('fontWeight'),
114        'line-height': $(this).css('lineHeight'),
115        'background-color': $(this).css('backgroundColor'),
116        'self': configCrayons.self
117      };
118      if (params['background-color'] == 'transparent'
119      || params['background-color'] == 'rgba(0, 0, 0, 0)') {
120        $(me).parents()
121        .each(function(){
122          var bg = $(this).css('backgroundColor');
123          if (bg != 'transparent'
124          && (params['background-color'] == 'transparent'
125          || params['background-color'] == 'rgba(0, 0, 0, 0)'))
126            params['background-color'] = bg;
127        });
128      }
129      $.post(configCrayons.url_crayons_html,
130        params,
131        function (c) {
132          eval('c = '+c); // JSON
133          $(me)
134          .find("em.crayon-searching")
135            .remove();
136          if (c.$erreur) {
137            uniAlert(c.$erreur);
138            return false;
139          }
140          id_crayon++;
141         
142          var position = 'absolute';
143          $(me).parents().each(function(){
144            if($(this).css("position") == "fixed")
145              position = 'fixed';
146          });
147
148          $(me)
149          .css('visibility','hidden')
150          .addClass('crayon-has')
151          .find('>.crayon-icones')
152            .attr('rel','crayon_'+id_crayon);
153          if ($.browser.msie) $(me).css({'zoom':1});
154          var pos = $(me).offset({'scroll':false});
155          $('<div class="crayon-html" id="crayon_'+id_crayon+'"></div>')
156          .css({
157            'position':position,
158            'top':pos['top']-1,
159            'left':pos['left']-1
160          })
161          .appendTo('body')
162          .html(c.$html);
163          $(me)
164          .activatecrayon(percent);
165        }
166      );
167    }
168  });
169};
170
171// annule le crayon ouvert (fonction destructive)
172$.fn.cancelcrayon = function() {
173  this
174    .filter('.crayon-has')
175    .css('visibility','visible')
176    .removeClass('crayon-has')
177    .removeClass('crayon-changed')
178  .crayon()
179    .remove();
180  return this;
181};
182
183// masque le crayon ouvert
184$.fn.hidecrayon = function() {
185  this
186  .filter('.crayon-has')
187  .css('visibility','visible')
188  .crayon()
189    .hide()
190    .removeClass('crayon-hover');
191  return this;
192};
193
194// active un crayon qui vient d'etre charge
195$.fn.activatecrayon = function(percent) {
196  this
197  .crayon()
198  .click(function(e){
199    e.stopPropagation();
200  });
201  this
202  .each(function(){
203    var me = $(this);
204    var crayon = $(this).crayon();
205    crayon
206    .find('form')
207      .append(
208        $('<input type="hidden" name="self" />')
209        .attr('value',configCrayons.self)
210      )
211      .ajaxForm({
212      "dataType":"json",
213      "success": function(d) {
214        me
215        .find("em.crayon-searching")
216          .remove();
217        if (d.$erreur > '') {
218          if (d.$annuler) {
219            if (d.$erreur > ' ') {
220              uniAlert(d.$erreur);
221            }
222            me
223            .cancelcrayon();
224          } else {
225              uniAlert(d.$erreur+'\n'+configCrayons.txt.error);
226              crayon
227              .find('form')
228                .css('opacity', 1.0)
229                .find(".crayon-boutons,.resizehandle")
230                  .show()
231                .end()
232                .find('.crayon-searching')
233                  .remove();
234          }
235          return false;
236        }
237        // Desactive celui pour qui on vient de recevoir les nouvelles donnees
238        $(me)
239        .cancelcrayon();
240        // Insere les donnees dans *tous* les elements ayant le meme code
241        $(
242          '.crayon.crayon-autorise.' +
243            me[0].className.match(/crayon ([^ ]+)/)[1]
244        )
245        .html(
246          d[$('input.crayon-id', crayon).val()]
247        )
248        .iconecrayon();
249      }})
250      .one('submit', function(){
251        crayon
252        .find('form')
253          .css('opacity', 0.5)
254          .after(configCrayons.mkimg('searching')) // icone d'attente
255          .find(".crayon-boutons,.resizehandle")
256            .hide();
257      })
258      // keyup pour les input et textarea ...
259      .keyup(function(e){
260        crayon
261        .find(".crayon-boutons")
262          .show();
263        me
264        .addClass('crayon-changed');
265        e.cancelBubble = true; // ne pas remonter l'evenement vers la page
266      })
267      // ... change pour les select : ici on submit direct, pourquoi pas
268      .change(function(e){
269        crayon
270        .find(".crayon-boutons")
271          .show();
272        me
273        .addClass('crayon-changed');
274        e.cancelBubble = true;
275      })
276      .keypress(function(e){
277        e.cancelBubble = true;
278      })
279      .find(".crayon-active[@type!=file]")
280        .each(function(n){
281          // focus pour commencer a taper son texte directement dans le champ
282          // on essaie de positionner la selection (la saisie) au niveau du clic
283          // ne pas le faire sur un input de [@type=file]
284          if (n==0) {
285            this.focus();
286            // premiere approximation, en fonction de la hauteur du clic
287            var position = parseInt(percent * this.textLength);
288            this.selectionStart=position;
289            this.selectionEnd=position;
290          }
291        })
292        .keydown(function(e){
293          if(!e.charCode && e.keyCode == 119 /* F8, windows */) {
294              crayon
295              .find("form.formulaire_crayon")
296              .submit();       
297          }       
298        })
299        .keypress(function(e){
300          if (e.keyCode == 27) {
301            me
302            .cancelcrayon();
303          }
304          // Clavier pour sauver
305          if (
306          (e.ctrlKey && (
307            /* ctrl-s ou ctrl-maj-S, firefox */
308            ((e.charCode||e.keyCode) == 115) || ((e.charCode||e.keyCode) == 83))
309            /* ctrl-s, safari */
310            || (e.charCode==19 && e.keyCode==19)
311          )
312          ) {
313            crayon
314            .find("form.formulaire_crayon")
315            .submit();
316          }
317          var maxh = this.className.match(/\bmaxheight(\d+)?\b/);
318          if (maxh) {
319            maxh = maxh[1] ? parseInt(maxh[1]) : 200;
320            maxh = this.scrollHeight < maxh ? this.scrollHeight : maxh;
321            if (maxh > this.clientHeight) {
322              $(this).css('height', maxh + 'px');
323            }
324          }
325        })
326      .end()
327      .find(".crayon-submit")
328        .click(function(e){
329          e.stopPropagation();
330          $(this)
331          .parents("form:eq(0)")
332          .submit();
333        })
334      .end()
335      .find(".crayon-cancel")
336        .click(function(e){
337          e.stopPropagation();
338          me
339          .cancelcrayon();
340        })
341      .end()
342      // decaler verticalement si la fenetre d'edition n'est pas visible
343      .each(function(){
344        var offset = $(this).offset({'scroll':false});
345        var hauteur = parseInt($(this).css('height'));
346        var scrolltop = $(window).scrollTop();
347        var h = $(window).height();
348        if (offset['top'] - 5 <= scrolltop)
349          $(window).scrollTop(offset['top'] - 5);
350        else if (offset['top'] + hauteur - h + 20 > scrolltop)
351          $(window).scrollTop(offset['top'] + hauteur - h + 30);
352        // Si c'est textarea, on essaie de caler verticalement son contenu
353        // et on lui ajoute un resizehandle
354        $("textarea", this)
355        .each(function(){
356          if (percent && this.scrollHeight > hauteur) {
357            this.scrollTop = this.scrollHeight * percent - hauteur;
358          }
359        })
360        .resizehandle()
361          // decaler les boutons qui suivent un resizer de 16px vers le haut
362          .next('.resizehandle')
363            .next('.crayon-boutons')
364            .css('margin-top', '-16px');
365      })
366    .end();
367  });
368};
369
370// insere les icones dans l'element
371$.fn.iconecrayon = function(){
372  return this.each(function() {
373    $(this).prepend(configCrayons.iconclick(this.className))
374    .find('.crayon-crayon, .crayon-img-changed') // le crayon a clicker lui-meme et sa memoire
375      .click(function(e){
376        $(this).parents('.crayon:eq(0)').opencrayon(e);
377      });
378    });
379};
380
381// initialise les crayons
382$.fn.initcrayon = function(){
383  this
384  .addClass('crayon-autorise')
385  .dblclick(function(e){
386    $(this).opencrayon(e,
387      // calcul du "percent" du click par rapport a la hauteur totale du div
388      ((e.pageY ? e.pageY : e.clientY) - document.body.scrollTop - this.offsetTop)
389      / this.clientHeight);
390  })
391  .iconecrayon();
392
393  // :hover pour MSIE
394  this.hover(
395    function(){
396      $(this)
397      .addClass('crayon-hover')
398      .find('>span.crayon-icones')
399        .find('>span>em.crayon-crayon,>span>em.crayon-edit')
400          .show();//'visibility','visible');
401    },function(){
402      $(this)
403      .removeClass('crayon-hover')
404      .find('>span.crayon-icones')
405        .find('>span>em.crayon-crayon,>span>em.crayon-edit')
406          .hide();//('visibility','hidden');
407    }
408  );
409
410  return this;
411};
412
413/* une fonction pour initialiser les crayons dynamiquement */
414$.fn.initcrayons = function(){
415  this
416  .find('.crayon')
417  .not('.crayon-autorise')
418  .filter(configCrayons.droits)
419  .initcrayon();
420};
421
422// demarrage
423$.fn.crayonsstart = function() {
424  if (!configCrayons.droits) return;
425  id_crayon = 0; // global
426
427  // sortie, demander pour sauvegarde si oubli
428  if (configCrayons.txt.sauvegarder) {
429    $(window).unload(function(e) {
430      var chg = $(".crayon-changed");
431      if (chg.length && uniConfirm(configCrayons.txt.sauvegarder)) {
432        chg.crayon().find('form').submit();
433      }
434    });
435  }
436
437  // on limite l'init auto aux 1000 premiers crayons
438  // setTimeout sert a passer en execution asynchrone pour confort d'affichage
439  if ((typeof crayons_init_dynamique == 'undefined') || (crayons_init_dynamique==false))
440    setTimeout(function(){
441      $(".crayon:lt(1000)")
442      .filter(configCrayons.droits)
443      .initcrayon();
444    }, 300);
445
446  // un clic en dehors ferme tous les crayons ouverts ?
447  if (configCrayons.cfg.clickhide)
448  $("html")
449  .click(function(){
450    $('.crayon-has')
451    .hidecrayon();
452  });
453};
454
455})(jQuery);
Note: See TracBrowser for help on using the repository browser.