【问题标题】:Dojo Tabs as Custom WidgetsDojo 选项卡作为自定义小部件
【发布时间】:2010-12-15 15:38:59
【问题描述】:

我创建了许多小部件,它们作为选项卡窗格加载到选项卡容器中。一切似乎都运行良好,除了我在使用自定义小部件与在标记中创建所有内容时得到不同的结果(标签内容没有占据整个页面,第 3 方小部件的行为不正常等)。这一切都让我认为我可能没有正确创建我的小部件。诀窍似乎是它们不会被解释为内容窗格。

我正在使用 dojo 1.3.2。

例如,以下标记效果很好:

<body class="soria" style="overflow-y: hidden;">
    <!-- Container for whole page -->
    <div dojoType="dijit.layout.BorderContainer" design="headline" id="borderContainer" style="height:100%;width:100%;">
        <!-- Header container -->
        <div dojoType="dijit.layout.ContentPane" region="top">
            Title
        </div>
        <!-- Left side -->
        <!--<div dojoType="dijit.layout.ContentPane" region="left" id="addressContainer" splitter="true" style="width:100%; background-color: #F0F8FF;">-->
        <div dojoType="dijit.layout.ContentPane" region="left" id="addressContainer" splitter="true">
            <div style="text-align: center;">
                <!-- address -->
                <span id="addressInstructions">Address Contents</span>
            </div>
        </div>
        <!-- Tabs -->
        <div dojoType="dijit.layout.TabContainer" id="tabs" region="center" tabPosition="top">
            <div dojoType="dijit.layout.ContentPane" id="tab1" title="map">
                <p>Change map to:</p>
                <div id="divMapList"></div>
                <div style="padding: 10px 10px 10px 10px;">
                    <div id="divMap" dojoAttachPoint="divMap" style="width:300px;height:300px;border:1px solid #000;display:block;margin-left:auto;margin-right:auto;"></div>
                </div>
            </div>
            <div dojoType="dijit.layout.ContentPane" id="tab2" title="other">
                Some text in here.
            </div>
        </div>
    </div>
</body>

查看生成的 HTML 代码,我可以看到选项卡本身具有以下类:“dijitContentPane dijitTabPane dijitTabContainerTop-child dijitTabContainerTop-dijitContentPane dijitVisible”。

以下是我的一个自定义小部件的 HTML:

<div>
    <div style="text-align: center; padding: 5px 5px 5px 5px;">
        <div>${i18nStrings.mapChangeMap}:</div>
        <div dojoAttachPoint="divMapSelection"></div>
        <div style="padding: 10px 10px 10px 10px;">
            <div id="divMap" dojoAttachPoint="divMap" style="width:300px;height:300px;border:1px solid #000;display:block;margin-left:auto;margin-right:auto;"></div>
        </div>
    </div>

这里是自定义小部件JS的一部分(如果需要我可以提供更多代码):

dojo.declare("xxxx.Widget.Map", [dijit._Widget, dijit._Templated],
{
    //Specify the path of the HTML file that sets the look of the widget
    templatePath: dojo.moduleUrl("xxxx", "widget/templates/Map.html"),

    //The strings used to populate standard text. Populated in postMixInProperties
    i18nStrings: null,

    //The widget's root div identifier. Value overwritten in postMixInProperties
    id:"tabMap",

    //The tab's title. Value overwritten in postMixInProperties
    title: "",

    //True to activate the tab. False otherwise.
    activate: false,

    //The map & current layer
    map: null,
    currentLayer: null,

    //Sets up some basic properties
    postMixInProperties: function() {
        this.inherited(arguments);
        var _1 = dojo.i18n.getLocalization("dijit", "loading", this.lang);
        this.loadingMessage = dojo.string.substitute(this.loadingMessage, _1);
        this.errorMessage = dojo.string.substitute(this.errorMessage, _1);
        if (!this.href && this.srcNodeRef && this.srcNodeRef.innerHTML) {
            this.isLoaded = true;
        }
        this.i18nStrings = dojo.i18n.getLocalization("IndyVIP","applicationStrings");
        this.title = this.i18nStrings.mapTabTitle;
    },
</div>

我通过创建小部件将小部件添加到容器中,然后将其作为子项添加到 tabcontainer。

这会导致以下类分配给我的选项卡:“dijitTabPane dijitTabContainerTop-child dijitVisible”。

有谁知道我做错了什么?

谢谢!

埃姆斯特

更新: 我决定尝试从 dijit.layout.ContentPane 和 dijit._Templated 继承。尽管如此,我仍然遇到问题,主要是如果我将小部件添加到 TabContainer,我会在 dojo.js.uncompressed.js 的第 4467 行收到错误“节点为空”,但选项卡似乎可以工作如果它是活动选项卡开始就好了。如果我将小部件添加到仅包含小部件的页面,它可以正常工作而不会出错。

请参阅下面的代码,它给了我预期的结果,但会导致一个“节点为空”错误。 HTML:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head>
    <title>Test</title>
    <script type="text/javascript">
        var djConfig = {
            parseOnLoad: true,
            useXDomain: true,
            debugAtAllCosts: true,
            baseUrl: './',
            modulePaths: {IndyVIP: 'js'}
        };
    </script>
    <link rel="Stylesheet" type="text/css" href="http://serverapi.arcgisonline.com/jsapi/arcgis/1.5/js/dojo/dijit/themes/soria/soria.css" />
    <script type="text/javascript" src="http://serverapi.arcgisonline.com/jsapi/arcgis/?v=1.5"></script>
    <script type="text/javascript">
        dojo.require("dojo.parser");
        dojo.require("dijit.layout.BorderContainer");
        dojo.require("dijit.layout.ContentPane");
        dojo.require("dijit.layout.TabContainer");
        dojo.require("IndyVIP.Widget.Map");
        dojo.addOnLoad(init);
        function init() {
            var tab = new IndyVIP.Widget.Map({title: 'Map'});
            var tabContainer = dijit.byId('tabs');
            tabContainer.addChild(tab);
        }
    </script>
</head>
<body class="soria" style="overflow-y: hidden;">
    <!-- Container for whole page -->
    <div dojoType="dijit.layout.BorderContainer" design="headline" id="borderContainer" style="height:100%;width:100%;">
        <!-- Header container -->
        <div dojoType="dijit.layout.ContentPane" region="top">
            Title
        </div>
        <!-- Left side -->
        <div dojoType="dijit.layout.ContentPane" region="left" id="addressContainer" splitter="true">
            <div style="text-align: center;">
                <!-- address -->
                <span id="addressInstructions">Address Contents</span>
            </div>
        </div>
        <!-- Tabs-->
        <div dojoType="dijit.layout.TabContainer" id="tabs" region="center" tabPosition="top">
            <!-- uncommenting the following results in map not acting the way it should -->
            <!--
            <div dojoType="dijit.layout.ContentPane" id="tab2" title="other">
                Some text in here.
            </div>-->
        </div>
    </div>
</body>
</html>

Map.js:

dojo.provide("IndyVIP.Widget.Map");
dojo.require("dijit.layout.ContentPane");
dojo.require("dijit._Templated");
dojo.require("dijit._Widget");

dojo.declare("IndyVIP.Widget.Map", [dijit.layout.ContentPane, dijit._Templated],
{
    map: null,

    //Specify the path of the HTML file that sets the look of the widget
    templatePath: dojo.moduleUrl("IndyVIP", "widget/templates/Map.html"),

    //The tab's title. Value overwritten in postMixInProperties
    title: "",

    widgetsInTemplate: true,

    startup: function() {
        this.map = new esri.Map('divMap');
        dojo.connect(this.map, 'onLayerAdd', this, this.onLayerAdd);
        var layer = new esri.layers.ArcGISTiledMapServiceLayer('http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer');
        this.map.addLayer(layer);
    },

    onLayerAdd: function() {
        //Create symbol
        var lineColor = new dojo.Color('black');
        var lineSymbol = new esri.symbol.SimpleLineSymbol(esri.symbol.SimpleLineSymbol.STYLE_SOLID,lineColor,1);
        var pointColor = new dojo.Color('red');
        var pointSymbol = new esri.symbol.SimpleMarkerSymbol(esri.symbol.SimpleMarkerSymbol.STYLE_CIRCLE,12,lineSymbol,pointColor);

        //Create point
        var x = 4.92;
        var y = 50.625;
        var point = new esri.geometry.Point(x,y,this.map.spatialReference);

        //Create template
        var template = new esri.InfoTemplate('A title','Some content');

        //Create graphic
        var graphic = new esri.Graphic(point,pointSymbol,null,template);

        //Add graphic to map
        this.map.graphics.clear();
        this.map.graphics.add(graphic);
    }

});

最后,这是小部件的 HTML 模板:

<div>
    <div id="divMap" dojoAttachPoint="divMap" style="width:300px;height:300px;border:1px solid #000;display:block;margin-left:auto;margin-right:auto;"></div>
</div>

到目前为止,我非常感谢您提出的所有建议。我觉得我错过了一些基本的东西,但我无法弄清楚。

埃姆斯特

【问题讨论】:

  • 明确一点,问题是您的内容没有填满内容窗格?当您说“第 3 方小部件的行为不正常”时,您是什么意思?
  • 这是问题的一部分,是的。我使用的第 3 方小部件是 ESRI 的 JavaScript API (resources.esri.com/arcgisserver/apis/javascript/arcgis/…)。我正在添加的地图没有正常运行。
  • 我昨天开始使用我的自定义小部件,而不是从 [dijit._Widget, dijit._Templated] 继承,我现在尝试从 [dijit.layout.ContentPane, dijit._Templated] 继承.我也遇到了错误,但我刚刚开始使用该选项。
  • 您是否尝试过在独立于容器的页面上测试您的小部件?看看你能不能让它出现在一个固定大小的 div 中,像这样:
    然后,您可以使用 dijit.byId('mywidget') 在 firebug 控制台中查看您的对象。我发现这对调试有很大帮助。如果您的小部件确实按预期工作,然后尝试调整包含的大小div 在运行时查看您的小部件如何响应。您的小部件可以在隐藏或 0 高度容器内创建。
  • 另外,您可能不想在小部件标记模板中的任何位置使用 DOM id 属性(例如 id="divMap")。创建小部件的多个实例将导致 DOM 节点具有相同的 id; dojoAttachPoint 就是您所需要的。

标签: dojo widget


【解决方案1】:

从 dijit.layout.ContentPane 继承时遇到的问题是我的小部件模板中的顶部 div 没有指定 dojoAttachPoint="containerNode"。这样做可以解决我遇到的“节点为空”错误。 我仍然遇到地图无法正常运行的问题,但这似乎与 dante 提示的选项卡最初不可见有关。

更新: 我遇到的另一个错误(地图没有按应有的方式运行)是由于小部件的模板 HTML 在小部件 HTML 中的地图上方有项目,如我上面的第一个示例(map.html)。在我提供的第二个示例中,我取出了多余的东西,从而解决了问题。

【讨论】:

    【解决方案2】:

    从 ContentPane 继承并在根节点上使用 dojoAttachPoint="containerNode" 似乎对于选项卡是强制性的。这帮助我解决了类似的问题。

    【讨论】:

      猜你喜欢
      • 2014-09-03
      • 2012-03-07
      • 2014-09-05
      • 2011-11-25
      • 1970-01-01
      • 2011-11-20
      • 2018-09-28
      • 1970-01-01
      • 2013-07-22
      相关资源
      最近更新 更多