【问题标题】:Allow users to select an arbitrary element on the page允许用户选择页面上的任意元素
【发布时间】:2010-07-16 22:55:55
【问题描述】:

我正在编写一个模板系统,该系统应该支持轻松地将任何旧的 html/xhtml 表单转换为可用于我的系统的格式(它是我的 cms 的模板系统)。

这是我的目标:

  1. 用户单击“区域定义”按钮,例如:“内容”、“侧边栏”等
  2. 当用户悬停任何元素时,它们会获得边框或以某种方式突出显示
  3. 如果用户单击该元素,则会将其修改为具有类似“zone-content”的类
  4. 页面通过 ajax 将新的 html 发送到脚本

是否有任何现有的库可以促进这样的事情?

更新:

我最终使用了下面的答案并一起编写了一个 jquery 解决方案(我们将在项目的其余部分使用 jquery)。它有点丑陋和hacky,但它有效 http://ilsken.com/labs/template/

【问题讨论】:

  • 为什么不直接使用 jQuery?使用该库实现这似乎相当简单......
  • 是的,但我想知道是否有任何插件/脚本已经这样做了,因为我对 javascript 不是很熟练

标签: php javascript jquery html ajax


【解决方案1】:

我个人是ExtJS (now Sencha) 的粉丝,使用该框架非常简单直接。我就是这样做的:

<body>
  <button id="content_define" class="zone_define">Content</button>
  <button id="sidebar_define" class="zone_define">Sidebar</button>
  <div id="template">
    <!-- put your template here -->
  </div>
</body>

<script type="text/javascript">
Ext.onReady(function() {
  Ext.select('button.zone_define').on('click', function(ev, target) {
    ev.stopEvent();

    // this listener is bound to two buttons, determine which one was pressed
    var zone = target.id.split('_')[0]; // 'content' or 'sidebar'

    // add a click listener listener to the template so that when an element within is clicked,
    // an Ajax request is initiated
    var template = Ext.get('template');
    template.addClass('targetable').on('click', function(ev, target) {
      template.removeClass('targetable');

      // this part is optional, in case the user clicks an <a> or <img> element,
      // you may want to get the block element containing the clicked element
      var target = ev.getTarget('div'); // or ul, table, p, whatever

      // invoke zone_capture on the click target (or containing block element)
      zone_capture(zone, target);
    }, window, {single: true});
    // the {single: true} part removes this listener after one click,
    // so the user has to go back and press the button again if they want to redefine
  });

  // this is the code to do the ajax request
  // and also add a class to the target element
  function zone_capture(zone, target) {
    // first, remove the class from elements which are already defined as this zone
    Ext.select(String.format('#template .{0}_zone', zone)).removeClass(zone + '_zone');

    // now add that class to the target
    target.addClass(zone + '_zone');

    // do the POST
    Ext.Ajax.request({
      method: 'POST',
      url: '/region/define',
      params: { // these are the params POSTed to your script
        template: Ext.get('template').dom.innerHTML
      }
    });
  }
});
</script>

我还会为悬停效果等添加以下 CSS 规则。

#template.targetable:hover div { /* add div, p, table, whatever */
  border: 1px solid #f00;
}

#template.targetable {
  cursor: crosshair;
}

我会称之为伪代码,但这个想法应该足以让你开始。由于您正在处理用户输入,因此在您将其称为生产就绪之前,您将需要检查很多极端情况。这听起来是一种很酷的方式来定义模板,祝你好运!

【讨论】:

  • 谢谢!如果项目启动,我会通知你的:P
【解决方案2】:

在普通的旧 jQuery 中,让我们看看我是否明白你的问题。首先,一些标记:

<div id="header"></div>

<div id="sidebar"></div>

<div id="main">
    <div class="moveable-element">
        <ul class="content-panel">
            <li><a href="#" id="header">Header</a></li>
            <li><a href="#" id="sidebar">Sidebar</a></li>
            <li><a href="#" id="main">Main</a></li>
            <li><a href="#" id="footer">Footer</a></li>
        </ul>
        <p>This is content in the moveable-element.</p>
    </div>
</div>

<div id="footer"></div>

还有 jQuery 脚本(类似这样):

$(function() {
    $('.moveable-element').hover(function() {
        $(this).find('.content-panel').show();
        $(this).css('border', '1px solid red');
    }, function() {
        $(this).find('.content-panel').hide();
        $(this).css('border', '1px solid black');
    }

    $('.content-panel a').click(function() {
        var class_name = $(this).attr("id");
        $(this).parents('.moveable-element').appendTo($('#'+class_name));
    }
}

还有一些 CSS 部分:

.content-panel {display: none; position: absolute;}
.moveable-element {border: 1px solid black; position: relative}

注意:我在您的问题中看不到 AJAX 的目的,请澄清。此外,这非常粗略,仅供参考,请不要指望它按原样开箱即用。如果你想让我修改它,我很乐意,尽管问。

【讨论】:

  • 在某种程度上这是我需要的,但问题是 html 不是由我控制的(我只是将脚本插入服务器端,或者使用小书签插入)。如果他们单击元素,脚本会将新的 html 发送到服务器以保存(基本上它会用 &lt;template:slot name="sidebar" /&gt;&lt;template:slot name="content" /&gt; 替换选定的元素,然后发送新的 html)
  • 这不是他想要做的。他有一个在文档中某处显示的模板,并且他有按钮,单击这些按钮时,您可以定义模板中的哪个元素应标识为“内容”、“侧边栏”等。用例是:1。单击侧边栏定义按钮, 2. 单击文档模板部分中的元素, 3. 用 CSS 类(或其他东西)指示单击的元素现在是侧边栏, 4. 将新模板文档提交到服务器,使用我们刚刚添加的 CSS 类(或其他)。
  • ^ 你解释了我想要的比我做得更好:P
【解决方案3】:

在 jQuery 中实现它很简单: 这个简单的示例如何在用户单击元素类时更改元素类

<script type="text/javascript">
         $('a').click(function(){
               $(this).attr('class','newClass');
          });
             //mouseover
         $('a').mouseover(function(){
               $(this).attr('class','newClass');
          });
</script>

【讨论】:

    猜你喜欢
    • 2021-12-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-01-03
    • 2012-09-24
    • 2012-05-30
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多