Skip to content

Commit

Permalink
change register API to sync with cy.Ext type
Browse files Browse the repository at this point in the history
  • Loading branch information
Atrue committed Oct 6, 2023
1 parent 8a4b18b commit c4a1a71
Show file tree
Hide file tree
Showing 7 changed files with 111 additions and 84 deletions.
57 changes: 43 additions & 14 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,39 +27,40 @@ ES import:

```js
import cytoscape from 'cytoscape';
import popper from 'cytoscape-popper';
import cytoscapePopper from 'cytoscape-popper';

function popperFactory(ref, content, opts) {
// use floating-ui or Tippy here. See demo
return {}
}

cytoscape.use( popper, popperFactory );
cytoscape.use( cytoscapePopper(popperFactory) );
```

CommonJS require:

```js
let cytoscape = require('cytoscape');
let popper = require('cytoscape-popper');
let cytoscapePopper = require('cytoscape-popper');

function popperFactory(ref, content, opts) {
// use floating-ui or Tippy here. See demo
return {}
}

cytoscape.use( popper, popperFactory ); // register extension
cytoscape.use( cytoscapePopper(popperFactory) ); // register extension
```

AMD:

```js
require(['cytoscape', 'cytoscape-popper'], function( cytoscape, popper ){
function popperFactory(ref, content, opts) {
// use floating-ui or Tippy here. See demo
return {}
}
// register extension
popper( cytoscape, function(ref, content, opts) {
// use floating-ui or Tippy here. See demo
return {}
} );
popper(popperFactory)(cytoscape);
});
```

Expand All @@ -71,15 +72,15 @@ This extension exposes `popper()` and `popperRef()` functions and provided `popp

Each function takes an options object, as follows:

`cy.popper( options )` or `ele.popper( options )` : Make a PopperInstance for the specified core Cytoscape instance or the specified element. This is useful for positioning a div relative to or on top of a core instance or element.
`cy.popper( options )` or `ele.popper( options )` : Make a `PopperInstance` for the specified core Cytoscape instance or the specified element. This is useful for positioning a div relative to or on top of a core instance or element.

`cy.popperRef( options )` or `ele.popperRef( options )` : Make a PopperInstance for the specified core Cytoscape instance or the specified element. A Popper virtual element is useful only for positioning, as it represent the target rather than the content. This is useful for cases where you want to create a new Popper instance manually via Popper constructor `createPopper()` or where you need to pass a `popperRef` object to another library like Tippy.js.
`cy.popperRef( options )` or `ele.popperRef( options )` : Make a `PopperInstance` for the specified core Cytoscape instance or the specified element. A Popper virtual element is useful only for positioning, as it represent the target rather than the content. This is useful for cases where you want to create a new Popper instance manually via Popper constructor `createPopper()` or where you need to pass a `popperRef` object to another library like Tippy.js.

- `options`
- `content` : The HTML content of the popper. May be a DOM `Element` reference or a function that returns one.
- `renderedPosition` : A function that can be used to override the [rendered Cytoscape position](http://js.cytoscape.org/#notation/position) of the Popper target. This option is mandatory when using Popper on the core. For an element, the centre of its bounding box is used by default.
- `renderedDimensions` : A function that can be used to override the [rendered](http://js.cytoscape.org/#notation/position) Cytoscape [bounding box dimensions](http://js.cytoscape.org/#eles.renderedBoundingBox) considered for the popper target (i.e. `cy` or `ele`). It defines only the effective width and height (`bb.w` and `bb.h`) of the Popper target. This option is more often useful for elements rather than for the core.
- `popper` : The PopperOptions object. These options are used in provided `popperFactory`.
- `popper` : The `PopperOptions` object. These options are used in provided `popperFactory`.

## Usage with @floating-ui

Expand All @@ -104,7 +105,7 @@ function popperFactory(ref, content, opts) {
return { update };
}

cytoscape.use(cytoscapePopper, popperFactory);
cytoscape.use(cytoscapePopper(popperFactory));
```

### `popper()` example
Expand Down Expand Up @@ -214,8 +215,7 @@ function tippyFactory(ref, content){
return tip;
}

cytoscape.use(cytoscapePopper, tippyFactory);

cytoscape.use(cytoscapePopper(tippyFactory));
```
The creation of many `Tippy` instances at once has performance implications, especially for large graphs. Create each instance on demand, e.g. on `tap`. Use [`destroy()`](https://atomiks.github.io/tippyjs/v6/methods/#destroy) instead of `hide()` where possible.

Expand All @@ -237,6 +237,35 @@ tip.show();

Refer to [Tippy.js](https://atomiks.github.io/tippyjs/) documentation for more details.

## v3 changes

Since `Popper.js` has become `@floating-ui` and the API has changed a lot it becomes harder to support both versions
(for example TippyJS, that supports only the previous version), so instead of depending on a specific external version
this extension allows users to use any Popper library with providing `popperFactory` function during initializing.

This version dropped the external dependency and changed the initializing api from `cytoscape.use(cytoscapePopper)` to `cytoscape.use(cytoscapePopper(popperFactory))`

See popperFactory examples to save backward-compatibility with v2


## Typescript

This extension export empty `PopperInstance` and `PopperOptions` interfaces allows to extend them according to the final Popper implementation.

`@floating-ui` example:
```ts
import { ComputePositionConfig } from '@floating-ui/dom';

declare module 'cytoscape-popper' {
interface PopperOptions extends ComputePositionConfig {
}
interface PopperInstance {
update(): void;
}
}

```

## Build targets

* `npm run test` : Run Mocha tests in `./test`
Expand Down
4 changes: 2 additions & 2 deletions cytoscape-popper.d.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import * as cy from "cytoscape";

declare const cytoscapePopper: cy.Ext;
declare const cytoscapePopper: (factory: cytoscapePopper.PopperFactory) => cy.Ext;
export = cytoscapePopper;
export as namespace cytoscapePopper;

Expand Down Expand Up @@ -46,7 +46,7 @@ declare namespace cytoscapePopper {

type getPopperRef<Type> = (opts?: Options<Type>) => RefElement;

type PopperFactory = (ref: RefElement, content: HTMLElement, options: PopperOptions) => PopperInstance;
type PopperFactory = (ref: RefElement, content: HTMLElement, options?: PopperOptions) => PopperInstance;
}

declare global {
Expand Down
98 changes: 49 additions & 49 deletions cytoscape-popper.js
Original file line number Diff line number Diff line change
Expand Up @@ -83,31 +83,6 @@ return /******/ (function(modules) { // webpackBootstrap
"use strict";


// Simple, internal Object.assign() polyfill for options objects etc.

module.exports = Object.assign != null ? Object.assign.bind(Object) : function (tgt) {
for (var _len = arguments.length, srcs = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
srcs[_key - 1] = arguments[_key];
}

srcs.forEach(function (src) {
if (src !== null && src !== undefined) {
Object.keys(src).forEach(function (k) {
return tgt[k] = src[k];
});
}
});

return tgt;
};

/***/ }),
/* 1 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


var _require = __webpack_require__(5),
getBoundingBox = _require.getBoundingBox;

Expand All @@ -130,29 +105,51 @@ function getRef(target, opts) {
module.exports = { getRef: getRef };

/***/ }),
/* 2 */
/* 1 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


var assign = __webpack_require__(0);
// Simple, internal Object.assign() polyfill for options objects etc.

var _require = __webpack_require__(1),
module.exports = Object.assign != null ? Object.assign.bind(Object) : function (tgt) {
for (var _len = arguments.length, srcs = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
srcs[_key - 1] = arguments[_key];
}

srcs.forEach(function (src) {
if (src !== null && src !== undefined) {
Object.keys(src).forEach(function (k) {
return tgt[k] = src[k];
});
}
});

return tgt;
};

/***/ }),
/* 2 */
/***/ (function(module, exports, __webpack_require__) {

"use strict";


var _require = __webpack_require__(0),
getRef = _require.getRef;

var _require2 = __webpack_require__(6),
getContent = _require2.getContent;

var popperDefaults = {};

// Create a new popper object for a core or element target


function getPopper(target, opts) {
var refObject = getRef(target, opts);
var content = getContent(target, opts.content);
var popperOpts = assign({}, popperDefaults, opts.popper);

return target.popperFactory(refObject, content, popperOpts);
return target.popperFactory(refObject, content, opts.popper);
}

module.exports = { getPopper: getPopper };
Expand All @@ -164,12 +161,12 @@ module.exports = { getPopper: getPopper };
"use strict";


var assign = __webpack_require__(0);
var assign = __webpack_require__(1);

var _require = __webpack_require__(2),
getPopper = _require.getPopper;

var _require2 = __webpack_require__(1),
var _require2 = __webpack_require__(0),
getRef = _require2.getRef;

function popper(opts) {
Expand Down Expand Up @@ -246,12 +243,12 @@ module.exports = { popper: popper, popperRef: popperRef };
"use strict";


var assign = __webpack_require__(0);
var assign = __webpack_require__(1);

var _require = __webpack_require__(2),
getPopper = _require.getPopper;

var _require2 = __webpack_require__(1),
var _require2 = __webpack_require__(0),
getRef = _require2.getRef;

function popper(opts) {
Expand Down Expand Up @@ -357,24 +354,27 @@ var coreImpl = __webpack_require__(4);
var collectionImpl = __webpack_require__(3);

// registers the extension on a cytoscape lib ref
var register = function register(cytoscape, popperFactory) {
if (!cytoscape) {
return;
} // can't register if cytoscape unspecified
var registerFactory = function registerFactory(popperFactory) {
if (typeof popperFactory !== "function") {
throw new Error('No \'popperFactory\' function specified');
throw new Error('Provide \'popperFactory\' before registering the module');
}

// register with cytoscape.js
cytoscape('core', 'popperFactory', popperFactory); // Cytoscape Core factory
cytoscape('collection', 'popperFactory', popperFactory); //Cytoscape Collections factory
cytoscape('core', 'popper', coreImpl.popper); //Cytoscape Core
cytoscape('collection', 'popper', collectionImpl.popper); //Cytoscape Collections
cytoscape('core', 'popperRef', coreImpl.popperRef); //Cytoscape Core for References
cytoscape('collection', 'popperRef', collectionImpl.popperRef); //Cytoscape Collections for References
return function register(cytoscape) {
if (!cytoscape) {
return;
} // can't register if cytoscape unspecified

// register with cytoscape.js
cytoscape('core', 'popperFactory', popperFactory); // Cytoscape Core factory
cytoscape('collection', 'popperFactory', popperFactory); //Cytoscape Collections factory
cytoscape('core', 'popper', coreImpl.popper); //Cytoscape Core
cytoscape('collection', 'popper', collectionImpl.popper); //Cytoscape Collections
cytoscape('core', 'popperRef', coreImpl.popperRef); //Cytoscape Core for References
cytoscape('collection', 'popperRef', collectionImpl.popperRef); //Cytoscape Collections for References
};
};

module.exports = register;
module.exports = registerFactory;

/***/ })
/******/ ]);
Expand Down
2 changes: 1 addition & 1 deletion demo-tippy.html
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@
}

document.addEventListener('DOMContentLoaded', function () {
cytoscape.use(cytoscapePopper, tippyFactory);
cytoscape.use(cytoscapePopper(tippyFactory));

var cy = window.cy = cytoscape({
container: document.getElementById('cy'),
Expand Down
2 changes: 1 addition & 1 deletion demo.html
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@
}

document.addEventListener('DOMContentLoaded', function () {
cytoscape.use(cytoscapePopper, popperFactory);
cytoscape.use(cytoscapePopper(popperFactory));

var cy = window.cy = cytoscape({
container: document.getElementById('cy'),
Expand Down
26 changes: 14 additions & 12 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,20 +2,22 @@ const coreImpl = require('./core');
const collectionImpl = require('./collection');

// registers the extension on a cytoscape lib ref
let register = function (cytoscape, popperFactory) {
if (!cytoscape) { return; } // can't register if cytoscape unspecified
let registerFactory = function(popperFactory) {
if (typeof popperFactory !== "function") {
throw new Error(`No 'popperFactory' function specified`);
throw new Error(`Provide 'popperFactory' before registering the module`);
}

// register with cytoscape.js
cytoscape('core', 'popperFactory', popperFactory); // Cytoscape Core factory
cytoscape('collection', 'popperFactory', popperFactory); //Cytoscape Collections factory
cytoscape('core', 'popper', coreImpl.popper); //Cytoscape Core
cytoscape('collection', 'popper', collectionImpl.popper); //Cytoscape Collections
cytoscape('core', 'popperRef', coreImpl.popperRef); //Cytoscape Core for References
cytoscape('collection', 'popperRef', collectionImpl.popperRef); //Cytoscape Collections for References
return function register(cytoscape) {
if (!cytoscape) { return; } // can't register if cytoscape unspecified

};
// register with cytoscape.js
cytoscape('core', 'popperFactory', popperFactory); // Cytoscape Core factory
cytoscape('collection', 'popperFactory', popperFactory); //Cytoscape Collections factory
cytoscape('core', 'popper', coreImpl.popper); //Cytoscape Core
cytoscape('collection', 'popper', collectionImpl.popper); //Cytoscape Collections
cytoscape('core', 'popperRef', coreImpl.popperRef); //Cytoscape Core for References
cytoscape('collection', 'popperRef', collectionImpl.popperRef); //Cytoscape Collections for References
};
} ;

module.exports = register;
module.exports = registerFactory;
6 changes: 1 addition & 5 deletions src/popper.js
Original file line number Diff line number Diff line change
@@ -1,16 +1,12 @@
const assign = require('./assign');
const { getRef } = require('./ref');
const { getContent } = require('./content');

const popperDefaults = {};

// Create a new popper object for a core or element target
function getPopper(target, opts) {
let refObject = getRef(target, opts);
let content = getContent(target, opts.content);
let popperOpts = assign({}, popperDefaults, opts.popper);

return target.popperFactory(refObject, content, popperOpts);
return target.popperFactory(refObject, content, opts.popper);
}

module.exports = { getPopper };

0 comments on commit c4a1a71

Please sign in to comment.