Closed GeorgeS2019 closed 2 years ago
var cy=cytoscape(.......); //this is method call, sort of window.cytoscape(...)
//this is not contructor and Window.Construct() will create constructor for it which is incorrect
to recreate this call we can use
//call method and get ptr
JObjPtr _cy = Window.CallRef("cytoscape",param); /* js reference to cytoscape */
Also the parameter to this function need some tweaking
{
container: document.getElementById('cy'),
elements: [
{ data: { id: 'a' } },
{ data: { id: 'b' } },
{
data: {
id: 'ab',
source: 'a',
target: 'b'
}
}]
}
Blazor provides a buitin class called ElementReference
to hold a HTML Element so when converting this parameter JS object to C# (autogenerated from JS -> JSON -> C# class. We can replace container with ElementReference
public class Param
{
public ElementReference container { get; set; }
public List<Element> elements { get; set; }
}
public class Data
{
public string id { get; set; }
public string source { get; set; }
public string target { get; set; }
}
public class Element
{
public Data data { get; set; }
}
Here is how your code will look like
@page "/"
@using BlazorBindGen
@using static BlazorBindGen.BindGen
@inject IJSRuntime runtime
<div id="cy" @ref="canvas" ></div>
@code
{
ElementReference canvas;
JWindow win;
protected override async Task OnInitializedAsync()
{
await base.OnInitializedAsync();
await Init(runtime);
win = Window;
await Draw();
}
//var cy = cytoscape({
//container: document.getElementById('cy'),
//elements: [
// { data: { id: 'a' } },
// { data: { id: 'b' } },
// {
// data: {
// id: 'ab',
// source: 'a',
// target: 'b'
// }
// }]
//});
async Task Draw()
{
await Import("https://cytoscape.org/cytoscape.js-tutorial-demo/js/cytoscape.min.js");
//converting param from JS object to C# Class (Convert first to JS->JSON->C# class using automatic generators)
var param = new Root
{
container = canvas,
elements=new List<Element>
{
new Element{data=new Data{id="a"}},
new Element{data=new Data{id="b"}},
new Element{data=new Data{id="ab",source="a",target="b"}},
}
};
JObjPtr _cy = Window.CallRef("cytoscape",param); /* js reference to cytoscape */
}
public class Data
{
public string id { get; set; }
public string source { get; set; }
public string target { get; set; }
}
public class Element
{
public Data data { get; set; }
}
public class Root
{
public ElementReference container { get; set; }
public List<Element> elements { get; set; }
}
}
<style>
#cy {
width: 100%;
height: 100%;
position: absolute;
top: 0px;
left: 0px;
}
</style>
Output:
<span class="oi oi-list-rich" aria-hidden="true"></span> CryptoScape
This should be
<span class="oi oi-list-rich" aria-hidden="true"></span> Cytoscape
Thank you for speedy response with advice!
@sps014 => I could not get it to display "RED hexagon"?
How to do ==> 'background-color': 'red',
Any suggestion?
{ container: document.getElementById('cy'), elements: [ // nodes { data: { id: 'a' } }, { data: { id: 'b' } }, // edges { data: { id: 'ab', source: 'a', target: 'b' } }, ], style: [ { selector: 'node', style: { shape: 'hexagon', 'background-color': 'red', label: 'data(id)' } }], layout: { name: 'grid' } }
var param = new Root { container = canvas, elements=new List<Element> { new Element{data=new Data{id="a"}}, new Element{data=new Data{id="b"}}, new Element{data=new Data{id="ab",source="a",target="b"}}, }, style = new List<Style> { new Style{ selector ="node"; Style = new StyleElement{ shape="hexagon"; label ="data(id)" } } } layout = new Layout{ name="grid" } }; /// Elements public class Element { public Data data { get; set; } } public class Data { public string id { get; set; } public string source { get; set; } public string target { get; set; } } /// Style public class Style { public string selector { get; set; } public StyleElement style { get; set; } } public class StyleElement { public string shape{ get; set; } public string label{ get; set; } } /// Layout public class Layout { public string name { get; set; } } public class Root { public ElementReference container { get; set; } public List<Element> elements { get; set; } public List<Style> style{ get; set; } public Layout layout { get; set; } }
<style> #cy { width: 400px; height: 400px; position: relative; top: 20px; left: 20px; border: 3px solid #73AD21; } </style>
On higher level you could create a property backgroundColor and annotate it with attribute
[JsonPropertyName("background-color")]
on higher level you can print that object and see if correct property names is generated JS side , otherwise it mght be a bug with Cytoscape.
Can you share your source code , so i can see what you are doing wrong
I think you could use your existing GraphDraw.razor to check the code https://github.com/sps014/BlazorBindGen/blob/main/SampleApp/Pages/GraphDraw.razor
This is how your object looks like JS side with
Window["console"].CallVoid("log", param);
This might be related to default value of null being passed in some not assigned properties, I would rather assign a valid default value to begin with.
look in style[1] background color
is assigned to null and for other's as well.
Is there a way to specify OptionalVariable so when it is not used, it is ignored?
Also you were using NewtonSoft.Json
use System.Text.Json
, your property name would look like
[JsonPropertyName("background-color")]
Style class in F#
https://github.com/fslaborg/Cyjs.NET/blob/main/src/Cyjs.NET/Style.fs
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
cy.CallVoid("layout", new { name= "circle"});
Also make ure cy
object has a function called layout
defined as indicated by these errors
How to format?
cy.CallVoid("style", "node { background-color: cyan; }"); <========work
cy.CallVoid("style", new { node { shape='hexagon'; background-color='blue', label='data(id)'}});
<==not work
Something like
class container
{
public Node node{get;set;}
}
class Node
{
[JsonPropertyName("background-color")]
public string backgroundColor{get;set;}
///.... etc
}
/*create a new instance of container and use constructor or property set */
cy.CallVoid("style", new container());
cy.style() .fromString('node { background-color: blue; }') .update() // update the elements in the graph with the new style ;
Is this possible using your framework??
Yes it is
cy.CallVoid("style().fromString", "node { background-color: green; }"); cy.CallVoid("update");
Not working, something I have done wrong?
cy.CallRef("style").CallRef("fromString","node {}").CallVoid("update");
Thx for creating this interesting framework. I was learning through the sample information provided.
I do not get any error and the expected result. Any suggestion?
Source Ref
cytoscape.razor
Source for working cytoscape.min.js
cytoscape.min.js
expected result