Лучший метод для окон / диалогов DHTML в Prototype? - PullRequest
1 голос
/ 12 февраля 2009

Я люблю Прототип , но он не поставляется ни с одним виджетом. В частности, он ничего не предоставляет для создания окон / диалогов.

Я попробовал библиотеку дополнений Prototype Window , но обнаружил, что она ненадежна и долго не поддерживается

У кого-нибудь есть рекомендуемые решения? Или какие-либо рецепты / шаблоны для создания диалога из первых принципов (т.е. без какой-либо библиотеки, кроме Prototype)? Мне нужно модальное поведение (с эффектом блеклого фона), и я должен поддерживать IE6, а также современные браузеры.

Просто чтобы прояснить ситуацию, я не собираюсь переключаться с Prototype и не хочу включать дополнительную базовую библиотеку, такую ​​как JQuery.

Ответы [ 3 ]

2 голосов
/ 12 февраля 2009

Есть несколько хороших сайтов для просмотра:

UI прототипа - с модальным диалогом.

Scripteka - Родина дополнений к Prototype. Здесь много хороших вещей.

1 голос
/ 17 февраля 2009

Для действительно простого диалога закажите этот код: http://snippets.dzone.com/posts/show/3411

Очень минималистично и просто - именно то, что я хотел.

Код прошел несколько модификаций. Вот окончательный вариант, который работал для меня:

/* 
 * Adapted from http://snippets.dzone.com/posts/show/3411
 */

var Dialog = {};
Dialog.Box = Class.create();
Object.extend(Dialog.Box.prototype, {
  initialize: function(id) {
    this.createOverlay();

    this.dialog_box = $(id);
    this.dialog_box.show = this.show.bind(this);
    this.dialog_box.persistent_show = this.persistent_show.bind(this);
    this.dialog_box.hide = this.hide.bind(this);

    this.parent_element = this.dialog_box.parentNode;

    this.dialog_box.style.position = "absolute";

    var e_dims = Element.getDimensions(this.dialog_box);
    var b_dims = Element.getDimensions(this.overlay);

    this.dialog_box.style.left = ((b_dims.width/2) - (e_dims.width/2)) + 'px';
    this.dialog_box.style.top = this.getScrollTop() + ((this.winHeight() - (e_dims.width/2))/2) + 'px';
    this.dialog_box.style.zIndex = this.overlay.style.zIndex + 1;
  },

  createOverlay: function() {
    if ($('dialog_overlay')) {
      this.overlay = $('dialog_overlay');
    } else {
      this.overlay = document.createElement('div');
      this.overlay.id = 'dialog_overlay';
      Object.extend(this.overlay.style, {
        position: 'absolute',
        top: 0,
        left: 0,
        zIndex: 90,
        width: '100%',
        backgroundColor: '#000',
        display: 'none'
      });
      document.body.insertBefore(this.overlay, document.body.childNodes[0]);
    }
  },

  moveDialogBox: function(where) {
    Element.remove(this.dialog_box);
    if (where == 'back')
      this.dialog_box = this.parent_element.appendChild(this.dialog_box);
    else
      this.dialog_box = this.overlay.parentNode.insertBefore(this.dialog_box, this.overlay);
  },

  show: function(optHeight/* optionally override the derived height, which often seems to be short. */) {
    this.overlay.style.height = this.winHeight()+'px';
    this.moveDialogBox('out');

    this.overlay.onclick = this.hide.bind(this);

    this.selectBoxes('hide');
    new Effect.Appear(this.overlay, {duration: 0.1, from: 0.0, to: 0.3});
    this.dialog_box.style.display = '';

    this.dialog_box.style.left = '0px';

    var e_dims = Element.getDimensions(this.dialog_box);

    this.dialog_box.style.left = (this.winWidth() - e_dims.width)/2 + 'px';

    var h = optHeight || (e_dims.height + 200);
    this.dialog_box.style.top = this.getScrollTop() + (this.winHeight() - h/2)/2 + 'px';
  },

  getScrollTop: function() {
    return (window.pageYOffset)?window.pageYOffset:(document.documentElement && document.documentElement.scrollTop)?document.documentElement.scrollTop:document.body.scrollTop;
  },

  persistent_show: function() {
    this.overlay.style.height = this.winHeight()+'px';
    this.moveDialogBox('out');

    this.selectBoxes('hide');
    new Effect.Appear(this.overlay, {duration: 0.1, from: 0.0, to: 0.3});

    this.dialog_box.style.display = '';
    this.dialog_box.style.left = '0px';
    var e_dims = Element.getDimensions(this.dialog_box);
    this.dialog_box.style.left = (this.winWidth()/2 - e_dims.width/2) + 'px';
  },

  hide: function() {
    this.selectBoxes('show');
    new Effect.Fade(this.overlay, {duration: 0.1});
    this.dialog_box.style.display = 'none';
    this.moveDialogBox('back');
    $A(this.dialog_box.getElementsByTagName('input')).each( function(e) {
      if (e.type != 'submit' && e.type != 'button') e.value = '';
    });
  },

  selectBoxes: function(what) {
    $A(document.getElementsByTagName('select')).each(function(select) {
      Element[what](select);
    });

    if (what == 'hide')
      $A(this.dialog_box.getElementsByTagName('select')).each(function(select){Element.show(select)})
  },

  winWidth: function() {
    if (typeof window.innerWidth != 'undefined')
       return window.innerWidth;
    if (typeof document.documentElement != 'undefined' && typeof document.documentElement.clientWidth != 'undefined' && document.documentElement.clientWidth != 0)
       return document.documentElement.clientWidth;
    return document.getElementsByTagName('body')[0].clientWidth
  },
  winHeight: function() {
    if (typeof window.innerHeight != 'undefined')
      return window.innerHeight
    if (typeof document.documentElement != 'undefined' && typeof document.documentElement.clientHeight != 'undefined' && document.documentElement.clientHeight != 0)
      return document.documentElement.clientHeight;
    return document.getElementsByTagName('body')[0].clientHeight;
  }

});
0 голосов
/ 12 февраля 2009

Scriptaculous - это библиотека пользовательского интерфейса / виджета / эффектов, созданная поверх Prototype. Вы обязательно найдете там то, что ищете.

...