diff --git a/template/index.html b/template/index.html
index ef6bc637e42bbdcdc1636498368e1300053b2fb8..260ca4d4048910b41ce7ca958b7e983e66bf1784 100644
--- a/template/index.html
+++ b/template/index.html
@@ -11,7 +11,7 @@
+
@@ -109,6 +109,7 @@
+
diff --git a/template/js/HoverMenuButton.js b/template/js/HoverMenuButton.js
new file mode 100644
index 0000000000000000000000000000000000000000..aa1c88d98c5cce537eec3b4f451893eb26539098
--- /dev/null
+++ b/template/js/HoverMenuButton.js
@@ -0,0 +1,120 @@
+/**
+ * Toolbar button with menu that appears when hovered over.
+ */
+Ext.define('Docs.HoverMenuButton', {
+ extend: 'Ext.toolbar.TextItem',
+ componentCls: "hover-menu-button",
+
+ /**
+ * @cfg {[String]} links
+ * Array of HTML anchor elements to be shown in menu.
+ */
+ links: [],
+
+ statics: {
+ // Global list of all menus.
+ // So we can hide all other menus while showing a specific one.
+ menus: []
+ },
+
+ initComponent: function() {
+ this.addEvents(
+ /**
+ * @event click
+ * Fired when button clicked.
+ */
+ "click"
+ );
+
+ // Append links count to button text
+ this.text += ' ' + this.links.length + '';
+
+ this.callParent(arguments);
+ },
+
+ onRender: function() {
+ this.callParent(arguments);
+
+ this.renderMenu();
+
+ this.getEl().on({
+ click: function() {
+ this.fireEvent("click");
+ },
+ mouseover: function() {
+ // hide other menus
+ Ext.Array.forEach(Docs.HoverMenuButton.menus, function(menu) {
+ if (menu !== this.menu) {
+ menu.setStyle({display: "none"});
+ }
+ });
+ // stop pending menuhide process
+ clearTimeout(this.hideTimeout);
+ // position menu right below button and show it
+ var p = this.getEl().getXY();
+ this.menu.setStyle({
+ left: p[0]+"px",
+ top: (p[1]+23)+"px",
+ display: "block"
+ });
+ },
+ mouseout: this.deferHideMenu,
+ scope: this
+ });
+
+ this.menu.on({
+ mouseover: function() {
+ clearTimeout(this.hideTimeout);
+ },
+ mouseout: this.deferHideMenu,
+ scope: this
+ });
+ },
+
+ onDestroy: function() {
+ // clean up DOM
+ this.menu.remove();
+ // remove from global menu list
+ Ext.Array.remove(Docs.HoverMenuButton.menus, this.menu);
+
+ this.callParent(arguments);
+ },
+
+ renderMenu: function() {
+ this.menu = Ext.get(Ext.core.DomHelper.append(document.body, {
+ html: this.renderMenuHtml(),
+ cls: 'hover-menu-menu'
+ }));
+ Docs.HoverMenuButton.menus.push(this.menu);
+ },
+
+ renderMenuHtml: function() {
+ // divide links into columns with at most 25 links in one column
+ var columns = [];
+ for (var i=0; i',
+ '',
+ '',
+ '',
+ '',
+ '{.}',
+ '',
+ ' | ',
+ '',
+ '
',
+ ''
+ );
+ return tpl.apply({columns: columns});
+ },
+
+ deferHideMenu: function() {
+ this.hideTimeout = Ext.Function.defer(function() {
+ this.menu.setStyle({display: "none"});
+ }, 200, this);
+ }
+
+});
diff --git a/template/js/OverviewToolbar.js b/template/js/OverviewToolbar.js
index 7e13ecc15e5a38898bb38269892b39101b02be79..167f629e73f5edf04d89251f05b6e06ba8e2e9e8 100644
--- a/template/js/OverviewToolbar.js
+++ b/template/js/OverviewToolbar.js
@@ -26,9 +26,9 @@ Ext.define('Docs.OverviewToolbar', {
var members = this.docClass[type];
if (members.length) {
this.items.push(this.createMemberButton({
- items: members,
+ text: memberTitles[type],
type: type,
- title: memberTitles[type]
+ members: members
}));
}
}
@@ -76,86 +76,16 @@ Ext.define('Docs.OverviewToolbar', {
},
createMemberButton: function(cfg) {
- var columns = [];
- for (var i=0; i',
- '',
- '',
- '',
- '',
- '{[this.renderLink(values)]}',
- '',
- ' | ',
- '',
- '
',
- '',
- {
- renderLink: Ext.bind(function(member) {
- return this.createLink(this.docClass.name, member);
- }, this)
- }
- );
-
- var menu = Ext.get(Ext.core.DomHelper.append(document.body, {
- html: tpl.apply({columns: columns}),
- style: "display: none; position: absolute",
- cls: 'member_sm'
- }));
- this.menus = this.menus || [];
- this.menus.push(menu);
-
- var timeout;
-
- return Ext.create('Ext.toolbar.TextItem', {
- cls: 'icon-' + cfg.type,
- style: "padding-left: 20px; cursor: pointer;",
- text: cfg.title + ' ' + cfg.items.length + '',
+ return Ext.create('Docs.HoverMenuButton', {
+ text: cfg.text,
+ cls: 'icon-'+cfg.type,
+ links: Ext.Array.map(cfg.members, function(m) {
+ return this.createLink(this.docClass.name, m);
+ }, this),
listeners: {
- render: function(item) {
- var el = item.getEl();
- el.on({
- click: function() {
- Ext.getCmp('doc-overview').scrollToEl("#m-" + cfg.type);
- },
- mouseover: function() {
- // hide other menus
- Ext.Array.forEach(this.menus, function(m) {
- if (m !== menu) {
- m.setStyle({display: "none"});
- }
- });
- clearTimeout(timeout);
- var p = el.getXY();
- menu.setStyle({left: p[0]+"px", top: (p[1]+23)+"px", display: "block"});
- },
- mouseout: function() {
- timeout = Ext.Function.defer(function() {
- menu.setStyle({display: "none"});
- }, 200);
- },
- scope: this
- });
- menu.on({
- mouseover: function() {
- clearTimeout(timeout);
- },
- mouseout: function() {
- timeout = Ext.Function.defer(function() {
- menu.setStyle({display: "none"});
- }, 200);
- },
- scope: this
- });
- },
- beforeDestroy: function() {
- // clean up DOM
- menu.remove();
- },
- scope: this
+ click: function() {
+ Ext.getCmp('doc-overview').scrollToEl("#m-" + cfg.type);
+ }
}
});
},
diff --git a/template/resources/sass/style.scss b/template/resources/sass/style.scss
index fecc9eb7d44b9768d0451f6564b26e5f6a384009..11c6aa59af580678d06b3eaae3d9fb8ea0a69b5b 100644
--- a/template/resources/sass/style.scss
+++ b/template/resources/sass/style.scss
@@ -754,7 +754,11 @@ pre, code, kbd, samp, tt {
background: url(../images/expandcollapse.png) no-repeat -14px 2px; }
.collapseAllMembers {
background: url(../images/expandcollapse.png) no-repeat 2px 2px; } }
-.member_sm {
+.hover-menu-button {
+ padding-left: 20px;
+ cursor: pointer; }
+.hover-menu-menu {
+ display: none; // hide initially
font-size: 12px;
position: absolute;
padding: 5px 15px 10px;
@@ -779,7 +783,7 @@ pre, code, kbd, samp, tt {
&:hover {
color: #083772;
text-decoration: underline; } }
- .l {
+ td {
vertical-align: top; } }
#doc-source {