css update on resize with angularjs - angularjs

I am trying to make a div that is a square, initialised at a width and a height of 25% of the width of the page. I want that the size of the div gets updated everytime i resize the browser to the right width and height. What am i doing wrong?
'use strict'
angular.module("cars4export.directives", []).directive('box', function($window) {
return {
restrict: "C",
link: function(scope, element, attrs) {
var width = $window.innerWidth * 0.25;
//initialising
element.css({
width: width,
height: width,
"font-size": width * 0.1,
paddingTop: width * 0.25,
paddingLeft: width * 0.3
});
//on resize
angular.element($window).bind('resize', function() {
element.css({
width: width,
height: width,
"font-size": width * 0.1,
paddingTop: width * 0.25,
paddingLeft: width * 0.3
});
scope.$apply();
})
}
}
})
.bleu {
background-color: #45619D;
color: white;
}
<div class="container-fluid" ng-controller="headerConfigController">
<div class="row">
<div class="col-md-3 bleu box">
<h4>Hello World</h4>
</div>
<div class="col-md-3">
</div><!--end logo-->
<div class="col-md-3">
</div><!--end menu-->
<div class="col-md-3">
</div><!--end newsletter-->
</div>
</div>

Related

I want to show a modal window on selecting a list item in angular js

I want to show a pop up window when a user selects an element from the dropdown list. But instead im getting a plain text no modal window is being shown. Please help: below is the referece for my code-
var app = angular.module('myApp', []);
app.controller('myCtrl', function($scope) {
$scope.value = '';
$scope.accntDetails = {
accnt01: { bankName: "HDFC", bankbranch: "delhi", accntNumber: "12345" },
accnt02: { bankName: "ICICI", bankbranch: "mumbai", accntNumber: "12346" },
accnt03: { bankName: "IDBI", bankbranch: "pune", accntNumber: "12347" }
};
$scope.modalShown = false;
$scope.toggleModal = function() {
$scope.modalShown = true;
};
$scope.changedValue = function(bank) {
$scope.value = bank.bankName;
$scope.toggleModal();
console.log($scope.value);
}
angular.module('myApp').directive('modalDialog', function() {
return {
restrict: 'E',
scope: {
show: '='
},
transclude: true,
link: function(scope, element, attrs) {
console.log('attrs: ', attrs);
scope.dialogStyle = {};
if (attrs.boxWidth) {
scope.dialogStyle.width = attrs.boxWidth;
}
if (attrs.boxHeight) {
scope.dialogStyle.height = attrs.boxHeight;
}
scope.hideModal = function() {
scope.modalShown = false;
};
},
template: `<div class='ng-modal' ng-show='modalShown'>
<div class='ng-modal-overlay' ng-click='hideModal()'></div>
<div class='ng-modal-dialog' ng-style='dialogStyle'>
<div class='ng-modal-close' ng-click='hideModal()'>X</div>
<div class='ng-modal-dialog-content' ng-transclude></div>
</div>
</div>`
};
});
});
/* Custom CSS- this is the css code for showing up a modal */
.ng-modal-overlay {
/* A dark translucent div that covers the whole screen */
position: absolute;
z-index: 9999;
top: 0;
left: 0;
width: 100%;
height: 100%;
background-color: #808080;
opacity: 0.8;
}
.ng-modal-dialog {
background-color: #fff;
box-shadow: 10px 10px #595554;
border-radius: 4px;
z-index: 10000;
position: absolute;
top: 50%;
left: 50%;
-ms-transform: translate(-50%, -50%);
-o-transform: translate(-50%, -50%);
-webkit-transform: translate(-50%, -50%);
-moz-transform: translate(-50%, -50%);
transform: translate(-50%, -50%);
}
.ng-modal-dialog-content {
padding: 10px;
text-align: left;
}
.ng-modal-close {
position: absolute;
top: 3px;
right: 5px;
padding: 5px;
cursor: pointer;
font-size: 120%;
display: inline-block;
font-weight: bold;
font-family: 'arial', 'sans-serif';
}
<body>
<div ng-app="myApp" ng-controller="myCtrl">
<p>Select account number:</p>
<!-- <select ng-model="accnt" ng-options="y.bankName for (x, y) in accntDetails">
</select> -->
<select ng-model="bankSelected" ng-change=" toggleModal();"
data-ng-options="bank as bank.bankName for bank in accntDetails">
<option value="">Select Account</option>
</select>
<h1>You selected: {{bankSelected.bankName}}</h1>
<h2>branch: {{bankSelected.bankbranch}}</h2>
<h3>Number: {{bankSelected.accntNumber}}</h3>
<div ng-show="modalShown">
<modal-dialog box-width="400px" box-height="150px">
<div class="row">
<div class="col-md-12">
<h3>Header</h3>
<hr style="border-top:1px solid darkblue" />
</div>
</div>
<div class="row">
<div class="col-md-12">
This is an important message
</div>
</div>
</modal-dialog>
</div>
</div>
</body>
when a user click on any element of the list a modal window should popup. I have tried this code. If i use it onClick event it works fine the modal opens but if i use it with ng-select it doesnt works:
Okay, I think there are two problems here. One is that your JSON is not valid to run on a repeat. It should be an array of Object to get the details. I was able to run the same when I tried that with the JSON as :
CODEPEN
like accntDetails = [{BankDetails1},{BankDetails2},{BankDetails}]

Angular gridster issues- resize and duplicate grids

I am trying to use angular gridster to have charts inside them. Below is the code which I am using. First thing is it doesnt allow me to move or resize any of these grids. Second its making each chart inside the grid repeat 4 times . Can anyone let me know what I could be doing wrong with the html or the configuration for gridster. I have referenced the css and js files for it correctly.
$scope.standardItems = [{
size: {
x: 2,
y: 2
},
position: [0, 0]
},
{
size: {
x: 2,
y: 2
},
position: [2, 0]
},
{
size: {
x: 2,
y: 3
},
position: [0, 2]
},
{
size: {
x: 1,
y: 1
},
position: [4, 2]
}
];
$scope.gridsterOpts = {
minRows: 2, // the minimum height of the grid, in rows
maxRows: 5,
columns: 1, // the width of the grid, in columns
colWidth: 'auto', // can be an integer or 'auto'. 'auto' uses the pixel width of the element divided by 'columns'
rowHeight: 'match', // can be an integer or 'match'. Match uses the colWidth, giving you square widgets.
margins: [10, 10], // the pixel distance between each widget
defaultSizeX: 2, // the default width of a gridster item, if not specifed
defaultSizeY: 1, // the default height of a gridster item, if not specified
minSizeX: 1, // minimum column width of an item
maxSizeX: null, // maximum column width of an item
minSizeY: 1, // minumum row height of an item
maxSizeY: null, // maximum row height of an item
isMobile: true, // stacks the grid items if true
mobileBreakPoint: 600, // if the screen is not wider that this, remove the grid layout and stack the items
mobileModeEnabled: true, // whether or not to toggle mobile mode when screen width is less than mobileBreakPoint
resizable: {
enabled: true,
start: function(event, uiWidget, $element) {}, // optional callback fired when resize is started,
resize: function(event, uiWidget, $element) {}, // optional callback fired when item is resized,
stop: function(event, uiWidget, $element) {} // optional callback fired when item is finished resizing
},
draggable: {
enabled: true, // whether dragging items is supported
handle: 'h5', // optional selector for resize handle
start: function(event, uiWidget, $element) {}, // optional callback fired when drag is started,
drag: function(event, uiWidget, $element) {}, // optional callback fired when item is moved,
stop: function(event, uiWidget, $element) {} // optional callback fired when item is finished dragging
}
};
<div gridster="gridsterOpts">
<ul>
<li style="border: solid 1px;" gridster-item="item" ng-repeat="item in standardItems">
<div class="container-fluid">
<div class="row">
<div class="col-md-4">
<h5>{{charts.data.chartsName[$parent.$index]}}</h5>
</div>
<div class="field-container" style="margin-top: 10px;">
<select class="form-control col-md-4" ng-change="charts.hasChanged[arrKey]" ng-model="charts.type[arrKey]" ng-init="charts.type[arrKey] = charts.data.chartsDefault[$parent.$index]">
<option ng-repeat="chartsTypeValue in charts.data.chartsType[arrKey] " >{{chartsTypeValue}}</option>
</select>
<!-- <label class="floating-label">Chart Type</label> -->
</div>
</div>
</div>
<div class="svg-container" ng-if="charts.type[arrKey] =='Bar'" style="width: 400px; height: 250px;">
<bars-chart ng-if="arrValue" chart-data="arrValue" />
</div>
<div class="svg-container " ng-if="charts.type[arrKey] =='Pie'" style="text-align: -webkit-center; width: 400px; height: 220px; ">
<donut-Chart ng-if="arrValue" chart-data="arrValue">
</donut-chart>
</div>
<div class="svg-container " ng-if="charts.type[arrKey]=='Line'" style="width: 400px; height: 220px; ">
<line-Chart ng-if="arrValue" chart-data="arrValue">
</line-chart>
</div>
<hr>
</li>
</ul>
</div>
</div>

Pie chart with data [] dont show any message

Hi everyone I have a pie chart made with nvd3 and when graph.data=[] it doenst show anything.. I want to display a simple message like "No data to show"
View:
<tab ng-if="dataConsNetfilter" heading="Summary" disable="!tabClick" active="true">
<p>{{dataConsNetfilter}}</p>
<div class="no-data" ng-if="dataConsNetfilter.data.length==0">
<img src="/assets/img/nodata.png"/>
<h3>No Data</h3>
</div>
<div class="col-md-12" style="text-align:center;margin-bottom:30px" ng-repeat="graph in dataConsNetfilter.types" resize>
<img ng-if="!graph.options" style="height:32px;margin:50px auto;" src="/assets/img/loader.gif" />
<div ng-if="graph.options && graph.data.length>0">
<center><nvd3 options='graph.options' data="graph.data"></nvd3></center>
<br>
</div>
</div>
</tab>
Logs from view:
{"types":[{"type":"netfilter.nfacct_bytes","options":{"chart":{"type":"pieChart","height":500,"width":1000,"margin":{"top":20,"right":20,"bottom":50,"left":55},"noData":"No data to show in the specified range","legend":{"rightAlign":false},"showValues":true,"legendPosition":"right","labelType":"percent","donut":true,"donutRatio":0.35,"duration":500,"xAxis":{"axisLabel":""},"yAxis":{"axisLabel":"Total","axisLabelDistance":-10}}},"data":[]}]}
Options:
var options = {
chart: {
type: 'pieChart',
height: 500,
width:1000,
margin : {
top: 20,
right: 20,
bottom: 50,
left: 55
},
noData: 'No data to show in the specified range',
legend: {
rightAlign:false,
},
valueFormat: function(d) {
return d.value;
},
x: function(d){return d.label;},
y: function(d){return d.value;},
showValues: true, //Display pie labels
legendPosition: 'right',
labelType: 'percent', //Configure what type of data to show in the label. Can be "key", "value" or "percent"
donut: true, //Turn on Donut mode. Makes pie chart look tasty!
donutRatio: 0.35, //Configure how big you want the donut hole size to be.
duration: 500,
xAxis: {
axisLabel: ''
},
yAxis: {
axisLabel: 'Total',
axisLabelDistance: -10
}
}
}
My tab is all blank and i want to show a message to inform the user... how to do this?
My solution was "ng-if="dataConsNetfilter.types[0].data.length==0"
<tab ng-if="dataConsNetfilter" heading="Summary" disable="!tabClick" active="true">
<p>{{dataConsNetfilter}}</p>
<div class="no-data" ng-if="dataConsNetfilter.types[0].data.length==0">
<img src="/assets/img/nodata.png"/>
<h3>No Data</h3>
</div>
<div class="col-md-12" style="text-align:center;margin-bottom:30px" ng-repeat="graph in dataConsNetfilter.types" resize>
<img ng-if="!graph.options" style="height:32px;margin:50px auto;" src="/assets/img/loader.gif" />
<div ng-if="graph.options && graph.data.length>0">
<center><nvd3 options='graph.options' data="graph.data"></nvd3></center>
<br>
</div>
</div>
</tab>

Difficulty getting JavaScript animation to work with AngularJS Directive

function percentToPixel(perc) {
return ($(".stepNavContainer").outerWidth() / 100) * parseFloat(perc);
}
var app = angular.module('app', ["ngAnimate"]);
app.controller("appController", function($scope) {
});
app.directive("init-modal", function() {
return {
restrict: 'E',
link: function(scope, element, attrs) {
scope.init = function() {
TweenMax.set($("#cursor"), {
x: percentToPixel("0") + "px",
xPercent: -50
});
TweenMax.set($("#joinModalNavStep1"), {
x: percentToPixel("0") + "px",
xPercent: -50
});
TweenMax.set($("#joinModalNavStep2"), {
x: percentToPixel("50") + "px",
xPercent: -50
});
TweenMax.set($("#joinModalNavStep3"), {
x: percentToPixel("100") + "px",
xPercent: -50
});
};
}
};
});
app.directive("step-modal", function() {
return {
restrict: 'E',
link: function(scope, element, attrs) {
var tlStepNavAnimation = new TimelineMax();
tlStepNavAnimation.to(cursor, 1, {
x: percentToPixel("0") + "px",
xPercent: -50,
ease: Back.easeInOut
});
tlStepNavAnimation.addPause();
tlStepNavAnimation.to(cursor, 1, {
x: percentToPixel("50") + "px",
xPercent: -50,
ease: Back.easeInOut
});
tlStepNavAnimation.addPause();
tlStepNavAnimation.to(cursor, 1, {
x: percentToPixel("100") + "px",
xPercent: -50,
ease: Back.easeInOut
});
scope.play = function() {
tlStepNavAnimation.play();
};
scope.reverse = function() {
tlStepNavAnimation.reverse();
};
}
};
});
html,
body {
overflow: hidden;
}
body {
background-color: white;
margin: 0;
padding: 0;
}
.stepNavContainer {
position: relative;
height: 50px;
width: 50%;
left: 25%;
border: 1px solid red;
}
.circle {
display: block;
position: absolute;
width: 50px;
height: 50px;
border-radius: 50%;
}
#cursor {
display: block;
position: absolute;
width: 50px;
height: 50px;
background: #c32026;
border-radius: 50%;
}
.step {
background: #999999;
}
.btn {
width: 100px;
height: 50px;
border: 1px solid black;
}
<!DOCTYPE html>
<html ng-app="app" ng-controller="appController">
<head>
<title>Title of the document</title>
<!-- Angular Material style sheet -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/angular-material/1.0.6/angular-material.min.css">
<link rel="stylesheet" href="style.css">
</head>
<body>
<div init-modal ng-click="init()" id="setupBtn" class="btn">
<span>Setup</span>
</div>
<div step-modal ng-click="reverse()" id="previousBtn" class="btn">
<span>Previous</span>
</div>
<div id="nextBtn" class="btn">
<span step-modal ng-click="play()">Next</span>
</div>
<div init-modal class="stepNavContainer">
<span id="joinModalNavStep1" class="circle step"></span>
<span id="joinModalNavStep2" class="circle step"></span>
<span id="joinModalNavStep3" class="circle step"></span>
<span id="cursor" class="circle"></span>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.0/angular-animate.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.2.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/1.18.2/TweenMax.min.js"></script>
</body>
</html>
So, I have a working JavaScript animation (Greensock) that you can see here http://codepen.io/jstafford/pen/VaLgvK . I am trying to plug this into an AngularJS directive, but I am not even making it inside the directives for Setup (init-modal directive) or Next and Previous (step-modal directive) buttons. 1) Push Setup button to setup the three circles and cursor at their initial positions which triggers the init-modal directive 2) Then the pushing of Next button or Previoius button triggers the step-modal directive to cause the step animation to occur. I am new to AngularJS and I am trying to do this the AngularJS way but really struggling. Any help greatly appreciated.
First, give a camel case name to your directive:
app.directive("initModal", function() {
return {
restrict: 'E',
link: function(){}
}
}
restrict: 'E' => Element: <init-modal></init-modal>
restrict: 'A' => Attribute: <div init-modal></div>
restrict: 'C' => Classname: <div class="init-modal"></div>
Angular's directive documentation

angular dragdrop (using jQuery UI) - disable swapping

I have problem with swapping the dragged/dropped elements.
DOM / Angular Structure:
angular.module('app', ['ngDragDrop'])
.controller('controller', function($scope) {
$scope.listItems = [
{name: "some name", title: "title"},
{name: "some name2", title: "title2"},
];
$scope.input = {};
$scope.draggableOprions = {
revert: 'invalid'
}
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script src="https://code.jquery.com/ui/1.10.3/jquery-ui.js"></script>
<script src="https://code.angularjs.org/1.4.9/angular.js"></script>
<script src="https://cdn.jsdelivr.net/angular.dragdrop/1.07/angular-dragdrop.min.js"></script>
<div ng-app="app">
<div ng-controller="controller">
<div class="container">
<ul>
<li data-drag="true"
data-jqyoui-options="draggableOprions"
jqyoui-draggable="{animate:true}"
ng-model="item" ng-repeat="item in listItems track by $index">
{{item.title}}
</li>
</ul>
</div>
<div class="container"
data-drop="true"
data-jqyoui-options jqyoui-droppable
ng-model="input">
<input ng-model="input.name">
</div>
</div>
</div>
The problem:
While I drag and drop an list item 1 - the name property of the list item 1 comes to the input model. But no longer is available in list item 1. Actually the list item 1 value goes undefined || null after I drop it in the input. If I now try to drag-n-drop list item 2 item in the input - the values swapping (list item 1 = undefined || null ? and list item 2 = list item 1 value and input model equal to list item 2 value`. So everything shuffle.
What I need:
I need to drag and drop list items in the input, avoiding losing values in list items. Every time i drop list item in the input, I need it's value to bind to the input.
Out of the box
I can change the drag and drop library, or even use source code, but the library is the better choice. I accept almost every good working answer which didn't broke any standards of good code (I mean that I need code which will not broke the other code and has good structure).
I suggest to use ngDraggable, an Angular module with no depency from jQuery or jQuery-ui.
Here below is a working snippet or check my Codepen:
angular.module('app', ['ngDraggable'])
.controller('controller', function($scope) {
$scope.listItems = [{
name: "some name",
title: "title1"
}, {
name: "some name2",
title: "title2"
}, {
name: "some name3",
title: "title3"
}, ];
$scope.droppedObjects = [];
$scope.input = {};
// drag complete over drop area
$scope.onDragComplete = function(data, evt) {
console.log("drag success, data:", data);
var index = $scope.droppedObjects.indexOf(data);
if (index > -1) {
$scope.droppedObjects.splice(index, 1);
}
}
// drop complete over drop area
$scope.onDropComplete = function(data, evt) {
console.log("drop success, data:", data);
var index = $scope.droppedObjects.indexOf(data);
if (index == -1)
$scope.droppedObjects.push(data);
}
// drop complete over input box
$scope.onDropCompleteInput = function(data, evt) {
console.log("drop on input success, data:", data);
$scope.input = data;
}
// drop complete over items area (remove from dropped list)
$scope.onDropCompleteRemove = function(data, evt) {
console.log("drop success - remove, data:", data);
var index = $scope.droppedObjects.indexOf(data);
if (index != -1)
$scope.droppedObjects.splice(index);
}
// other draggable events handlers
var onDraggableEvent = function(evt, data) {
console.log("128", "onDraggableEvent", evt, data);
}
$scope.$on('draggable:start', onDraggableEvent);
//$scope.$on('draggable:move', onDraggableEvent);
$scope.$on('draggable:end', onDraggableEvent);
});
* {
-moz-box-sizing: border-box;
-webkit-box-sizing: border-box;
box-sizing: border-box;
}
[ng-drag] {
-moz-user-select: -moz-none;
-khtml-user-select: none;
-webkit-user-select: none;
-ms-user-select: none;
user-select: none;
}
.item {
width: 100px;
height: 60px;
background: rgba(255, 0, 0, 0.5);
color: white;
text-align: center;
padding-top: 5%;
display: inline-block;
margin: 0 10px;
cursor: move;
}
ul.draggable-objects:after {
display: block;
content: "";
clear: both;
}
.draggable-objects li {
float: left;
display: block;
width: 120px;
height: 100px;
}
[ng-drag].drag-over {
border: solid 1px red;
}
[ng-drag].dragging {
opacity: 0.5;
}
.drop-container {
background: rgba(0, 255, 0, 0.5);
text-align: center;
width: 600px;
height: 200px;
padding-top: 90px;
display: block;
margin: 20px auto;
position: relative;
}
.drop-input {
width: 200px;
height: 40px;
}
.drag-enter {
border: solid 5px red;
}
.drop-container span.title {
display: block;
position: absolute;
top: 10%;
left: 50%;
width: 200px;
height: 20px;
margin-left: -100px;
margin-top: -10px;
}
.drop-container div {
position: relative;
z-index: 2;
}
<script src="//code.angularjs.org/1.4.8/angular.js"></script>
<script src="//rawgit.com/fatlinesofcode/ngDraggable/master/ngDraggable.js"></script>
<body ng-app="app">
<div ng-controller="controller">
<div class="row">
<h1>ngDraggable Example</h1>
</div>
<div ng-drop="true" ng-drop-success="onDropCompleteRemove($data,$event)">
<ul class="draggable-objects">
<li ng-repeat="obj in listItems">
<div ng-drag="true" ng-drag-data="obj" data-allow-transform="true" class="item"> {{obj.title}} </div>
</li>
</ul>
</div>
<hr/>
<div ng-drop="true" ng-drop-success="onDropComplete($data,$event)" class="drop-container">
<span class="title">Drop area</span>
<div ng-repeat="obj in droppedObjects" ng-drag="true" ng-drag-data="obj" ng-drag-success="onDragComplete($data,$event)" class="item">
{{obj.title}}
</div>
</div>
<hr/>
<div class="container">
Drop on input:
<input ng-model="input.name" class="drop-input" ng-drop="true" ng-drop-success="onDropCompleteInput($data,$event)">
</div>
<br>
<hr/>
<pre>listItems = {{listItems|json}}</pre>
<pre>input = {{input|json}}</pre>
<pre>droppedObjects = {{droppedObjects|json}}</pre>
</div>
</body>
<!DOCTYPE html>
<html>
<link rel="stylesheet" type="text/css" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css">
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script src="https://code.jquery.com/ui/1.10.3/jquery-ui.js"></script>
<script src="https://code.angularjs.org/1.4.9/angular.js"></script>
<script src="https://cdn.jsdelivr.net/angular.dragdrop/1.07/angular-dragdrop.min.js"></script>
<body>
<div ng-app="myApp" ng-controller="MyController">
<div id="products">
<h1 class="ui-widget-header">Products</h1>
<div id="catalog">
<div>
<ul>
<li ng-repeat='item in list1' ng-show="item.title" data-drag="true" data-jqyoui-options="{revert: 'invalid', helper: 'clone'}" ng-model="list1" jqyoui-draggable="{index: {{$index}}, animate: true, placeholder: 'keep'}">{{item.title}}</li>
</ul>
</div>
</div>
</div>
<div id="cart">
<h1 class="ui-widget-header">Shopping Cart</h1>
<div class="ui-widget-content">
<ol data-drop="true" ng-model='list4' jqyoui-droppable="{multiple:true}">
<li ng-repeat="item in list4 track by $index" ng-show="item.title" data-drag="true" data-jqyoui-options="{revert: 'invalid', helper: 'clone'}" ng-model="list4" jqyoui-draggable="{index: {{$index}},animate:true}">{{item.title}}</li>
<li class="placeholder" ng-hide="hideMe()">Add your items here</li>
</ol>
</div>
</div>
</div>
<script>
var app = angular.module('myApp', ['ngDragDrop']);
app.controller('MyController', function ($scope,$http,$sce)
{
$scope.list1 = [{'title': 'Lolcat Shirt'},{'title': 'Cheezeburger Shirt'},{'title': 'Buckit Shirt'}];
$scope.list4 = [];
$scope.hideMe = function()
{
return $scope.list4.length > 0;
}
});
</script>
</body>
</html>
You have to use helper: 'clone' in data-jqyoui-options

Resources