Dependent field in Laravel Nova using Nova Dependency Container - laravel

I'm quite new to Laravel Nova, and I'm trying to implement dependent fields but there's no easy solution to it. I want to display a checkbox if a certain value is selected in a select dropdown.
After a little searching, I found this: https://github.com/epartment/nova-dependency-container. I'm trying to use this, but something's not working right. I'm using Laravel v5.7 and Nova v1.3.2. Hence, I've installed v1.1.2 of this package.
I followed the installation guidelines and have written the following code:
<?php
namespace App\Nova;
...
use Epartment\NovaDependencyContainer\HasDependencies;
use Epartment\NovaDependencyContainer\NovaDependencyContainer;
...
class Submission extends Resource
{
use HasDependencies;
....
public function fields(Request $request)
{
$fields[] = Select::make('Route', 'route')->options([
0 => 'First Name',
1 => 'First Name / Last Name',
2 => 'Full Name'
])->displayUsingLabels();
$fields[] = NovaDependencyContainer::make([
Text::make('Title', 'title')
])->dependsOn('route', 2);
...
return $fields;
}
....
}
?>
I can see the field Route with the right options and values. However, when I select 'Full Name', the dependent field Title is not displayed.
When I see the JSON response of the fields, this is what I get:
...
{
"component": "select-field",
"prefixComponent": true,
"indexName": "Route",
"name": "Route",
"attribute": "route",
"value": null,
"panel": null,
"sortable": false,
"textAlign": "left",
"options": [
{
"label": "First Name",
"value": 0
},
{
"label": "First Name / Last Name",
"value": 1
},
{
"label": "Full Name",
"value": 2
}
]
},
{
"component": "nova-dependency-container",
"prefixComponent": true,
"indexName": "",
"name": "",
"attribute": "",
"value": [],
"panel": null,
"sortable": false,
"textAlign": "left",
"fields": [
{
"component": "text-field",
"prefixComponent": true,
"indexName": "Title",
"name": "Title",
"attribute": "title",
"value": null,
"panel": null,
"sortable": false,
"textAlign": "left"
}
],
"dependencies": [
{
"field": "route",
"value": 2
}
]
},
...
I'm not sure where I'm going wrong. Would be great if someone could guide me here. Or if there's another solution that works.
Thanks!

Related

Handling events in interactive Vega legends - race condtion

The linked chart contains only a legend and the legend works as follows:
clicking on a fruit name toggles it on and off
shift-clicking on a fruit name switches it ON and switches OFF all other fruit names
Legend display is controlled by two entities:
data set SELECTED remembers selected items
signal FILTERMODE toggles the type of the filter between include and exclude
Currently, if only one fruit name is ON, then a click on it switches it OFF (so all fruit names become OFF).
I would like to modify this behavior so that a click on the last enabled fruit name would switch everything ON.
(In other words - it would not be possible to deselect everything.)
In order to switch everything ON I only need to change the value of signal FILTERMODE to exclude. This is where I hit a snag.
I have tried the following in the signal definition:
"update": "event.shiftKey? 'include' : (length(data('selected'))? filtermode : 'exclude')",
This does not work. I am fairly sure this happens because of a race condition.
When I check for the length of data('source'), it is still non-empty.
So the sequence of events is the following:
click
update signal FILTERMODE (check if the data set SELECTED is empty - it is not)
update data set SELECTED (only now it has become empty)
What would be the most elegant work-around?
Try this instead. It is the same as your code but also checks the length of the array which your single line doesn't currently do.
You can now shift click melon and then click it normally and the filter mode will switch.
Editor
{
"$schema": "https://vega.github.io/schema/vega/v5.json",
"description": "A scatter plot example with interactive legend and x-axis.",
"width": 200,
"height": 200,
"padding": 5,
"autosize": "pad",
"signals": [
{
"name": "shift",
"value": false,
"on": [
{
"events": "#legendSymbol:click, #legendLabel:click",
"update": "event.shiftKey",
"force": true
}
]
},
{
"name": "clicked",
"value": null,
"on": [
{
"events": "#legendSymbol:click, #legendLabel:click",
"update": "{value: datum.value}",
"force": true
}
]
},
{
"name": "filtermode",
"value": "exclude",
"on": [
{
"events": "#legendSymbol:click, #legendLabel:click",
"update": "event.shiftKey? 'include' : (length(data('selected') == 0)? filtermode : 'exclude')",
"force": true
}
]
}
],
"data": [
{
"name": "source",
"values": [
{"fruit": "apple"},
{"fruit": "plum"},
{"fruit": "pear"},
{"fruit": "melon"},
{"fruit": "grape"},
{"fruit": "strawberry"}
]
},
{
"name": "selected",
"on": [
{"trigger": "clicked && (event.shiftKey)", "remove": true},
{"trigger": "clicked && (event.shiftKey)", "insert": "clicked"},
{"trigger": "clicked && (!event.shiftKey)", "toggle": "clicked"}
]
}
],
"scales": [
{
"name": "color",
"type": "ordinal",
"range": {"scheme": "category10"},
"domain": {"data": "source", "field": "fruit"}
}
],
"legends": [
{
"stroke": "color",
"title": "Fruit",
"encode": {
"symbols": {
"name": "legendSymbol",
"interactive": true,
"update": {
"fill": {"value": "transparent"},
"strokeWidth": {"value": 2},
"opacity": [
{
"test": "filtermode == 'exclude' && !indata('selected', 'value', datum.value)",
"value": 1
},
{
"test": "filtermode == 'include' && indata('selected', 'value', datum.value)",
"value": 1
},
{"value": 0.15}
],
"size": {"value": 64}
}
},
"labels": {
"name": "legendLabel",
"interactive": true,
"update": {
"opacity": [
{
"test": "filtermode == 'exclude' && !indata('selected', 'value', datum.value)",
"value": 1
},
{
"test": "filtermode == 'include' && indata('selected', 'value', datum.value)",
"value": 1
},
{"value": 0.25}
]
}
}
}
}
]
}
Are you checking the length of the correct array? It is hard to understand precisely what the desired behaviour is but if I add the code (depending on whether filter mode is include or exclude)
length(data('selected')) == 6
or
length(data('selected')) == 0
then it seems to work.
Editor

contentful graphql nested structure

I have a page in contentful which I retrieve content to my react app with graphql.
In this page, a link a content model called Person which is like that:
{
"name": "Person",
"description": "",
"displayField": "name",
"fields": [
{
"id": "name",
"name": "Name",
"type": "Symbol",
"localized": false,
"required": true,
"validations": [],
"disabled": false,
"omitted": false
},
{
"id": "profilePic",
"name": "profile pic",
"type": "Link",
"localized": false,
"required": true,
"validations": [],
"disabled": false,
"omitted": false,
"linkType": "Asset"
},
{
"id": "socialLinks",
"name": "social links",
"type": "Array",
"localized": false,
"required": false,
"validations": [],
"disabled": false,
"omitted": false,
"items": {
"type": "Link",
"validations": [
{
"linkContentType": [
"socialLink"
]
}
],
"linkType": "Entry"
}
}
ProfilePic is another content model which include name and picUrl.
SocialLinks is an array of socialLink content model which contain name and link
I can retrieve without problem my profilePic name or picUrl but I cannot get the socialLinks.
I have read the contentful documentation about one-to-many but is not clear to me how to apply to my case: https://www.contentful.com/developers/docs/references/graphql/#/reference/schema-generation/one-to-many-multi-type-relationships
My query:
...rest of the query..
founder{
name,
profilePic{
url,
title
},
socialLinksCollection {
items {
name,
link
}
}
},
... rest of the query...
Can somoene help me understand why it doesn't work as a normal collection?
Should I maybe use this concept of linkedFrom? But how exactly?
I had to add (limit: 1) to my socialLinksCollections otehrwise there were too many calls and wasn't possible to get the data back.
Thanks to #stefan judis for the suggestion where to look out for the errors.

Setting "Additional Field Options" for thumbnails in Voyager

I would like to use thumbnails in my blog posts. In the Post-model I need to write this:
use TCG\Voyager\Traits\Resizable;
class Post extends Model
{
use Resizable;
}
Then there is an other settings piece:
{
"resize": {
"width": "1000",
"height": null
},
"quality" : "70%",
"upsize" : true,
"thumbnails": [
{
"name": "medium",
"scale": "50%"
},
{
"name": "small",
"scale": "25%"
},
{
"name": "cropped",
"crop": {
"width": "300",
"height": "250"
}
}
]
}
Where does the settings part go?
And, how do I generate the thumbnails after that?
Sources:
https://voyager.readme.io/docs/thumbnails-url
https://voyager.readme.io/docs/additional-field-options#section-image
Settings should be written in the BREAD page for your table in front of the image form field.

Group array items with eloquent

I have the following eloquent query:
$extras = EventExtra::select('id', 'category', 'name', 'price', 'description', 'company')->get();
It gets some data from me from my database. What i want is for the returned data to be grouped twice, first by the category and then second by the company so that in the end i have something like this returned to the client:
[
{
"name": "donation",
"collection": [
{
"name": "sampleCompany1",
"array": [
{
"name": "extra1",
"description": "",
"value": ""
},
{
"name": "extra4",
"description": "",
"value": ""
},
{
"name": "extra6",
"description": "",
"value": ""
}
]
}
]
},
{
"name": "donation",
"collection": [
{
"name": "sampleCompany2",
"array": [
{
"name": "extra2",
"description": "",
"value": ""
},
{
"name": "extra3",
"description": "",
"value": ""
}
]
}
]
}]
I just typed the above myself so it might not be valid object array but basically it shows what i want to accomplish here.
You can use Collection to build your custom object. Something like this:
$return_data = Collect();
To add items in the collection with a property, you can use the put function.
$inner_data->put('name',$extras->name);
You can also add a collection within a collection.
To just push an existing collection in the collection, use push function
$inner_data->push($some_collection)
EDIT: Since you want a working example, see this below:
Lets say you want to create the following using collection:
{
"name": "extra1"
"description": "",
"value": ""
}
You will do something like this:
$my_collection = Collect();
$my_collection->put('name','extra1');
$my_collection->put('description','');
$my_collection->put('value','');
Now you can add this collection to another collection where you don't need a key. So lets say now it looks like this:
[
{
"name": "extra1"
"description": "",
"value": ""
},
{
"name": "extra4"
"description": "",
"value": ""
}
]
You will now do:
$my_final_collection = Collect();
foreach($my_collections as $my_collection) {
$my_final_collection->push($my_collection); // and so on in a loop
}

Display enum property of model definitions

i am trying to display the enum of a model in the model description.
The schema of my model is defined under definitions and uses an enum for the action property, because only this three types are allowed. (see code below)
I am using swagger version 2.0. In version 1.2 this seems to work: http://petstore.swagger.wordnik.com/ you can find the example under store/order.
they also use an enum and this is displayed behind the property in the model view.
How can i achieve the same result with the new version?
Thanks for help!
"paths": {
"/event": {
"post": {
"tags": [
"event"
],
"summary": "Add an new Event.",
"description": "TEST",
"operationId": "addEvent",
"consumes": [
"application/json"
],
"produces": [
"application/json"
],
"parameters": [
{
"in": "body",
"name": "data",
"description": "",
"required": true,
"schema": {
"$ref": "#/definitions/Event"
}
}
],
"responses": {
"405": {
"description": "Invalid input"
}
}
}
}
}
"definitions": {
"Event": {
"id": "eventModel",
"required": [
"action"
],
"properties": {
"action": {
"type": "string",
"default": "START",
"enum": [
"START",
"UPDATE",
"END"
],
"description": "blabla"
}
}
}
}
PS: another mistake i recognized right now, is that the shown model description of arrays misses the closing bracket ].
Your definition is fine, there's a known bug in swagger-ui - https://github.com/swagger-api/swagger-ui/issues/672. Feel free to subscribe the issue and follow the progress there.
As a side note, there's no "id" property in models in Swagger 2.0.

Resources