Vis Timeline - I don't want to change item.start and move. But i need to change item.end? - vis.js

I have one item. And item is fixed for item.start, and item shall not be moved. I need to change just item.end.
I was trying something. For example if item.class name is record-scheduled, item.start should be in the future. This code worked. But I couldn't build for start is constant.
onMoving: function (item, callback) {
if(item.className == 'record-scheduled'){
var min = moment()
var max = moment(item.start).add(6,'hours')
if (item.start < min) item.start = min;
if (item.start > max) item.start = max;
if (item.end > max) item.end = max;
callback(item); // send back the (possibly) changed item
}else if(item.className == 'record-finished'){
callback(null)
}else if(item.className =='record-active'){
callback(item)
}
else{
callback(item)
}
},
My timeline options:
options: {
editable: true,
stack: false,
start:moment().format(),
}
explain is briefly:
else if(item.className =='record-active'){
item.start = 'cannot be changed'
item.end = 'can be change'
item.draggable = 'cannot be draggable'
}
How could i solve it?
Thanks, Regards.

I thought of a new solution while opening the thread. Maybe It's not best way but the way worked for me. But you have to database. I didn't find how to get beforeItemStart other way. Maybe somebody help us for this. And my my solution is like;
else if(item.className =='record-active'){
axios
.get('http://localhost:3000/' + item.id)
.then(response => (this.selectedItem = response.data))
var findstarttime = new Long(this.selectedItem.StartDateTime.Ticks.low,
this.selectedItem.StartDateTime.Ticks.high,false).toNumber();
var oneZeroGoneFindStartTime = findstarttime / 10000
var findedstarttime = moment(oneZeroGoneFindStartTime)
console.log(findedstarttime)
var beforeItemStart = findedstarttime
if(beforeItemStart < item.start) item.start = beforeItemStart;
if(beforeItemStart > item.start) item.start = beforeItemStart;
callback(item)
}
I find beforeItemStart and It's always item.start = beforeItemStart.
And It can't draggable, just I can change end range. But here an axios causes too many queries. I need to fix that. Maybe it will be a solution for someone until a better answer comes.
Thanks, Regards.

Related

How to get simple face detection working?

I am trying to get a simple example of face detection working with ML Kit on iOS. Here is excerpts of the Objective C code:
FIRVisionFaceDetectorOptions *faceDetectorOptions;
FIRVision *vision;
FIRVisionFaceDetector *faceDetector;
faceDetectorOptions = [[FIRVisionFaceDetectorOptions alloc] init];
faceDetectorOptions.performanceMode = FIRVisionFaceDetectorPerformanceModeAccurate;
faceDetectorOptions.landmarkMode = FIRVisionFaceDetectorLandmarkModeAll;
faceDetectorOptions.contourMode = FIRVisionFaceDetectorContourModeNone;
faceDetectorOptions.classificationMode = FIRVisionFaceDetectorClassificationModeAll;
faceDetectorOptions.minFaceSize = 0.1; // TODO: finalize this option value
vision = [FIRVision vision];
faceDetector = [vision faceDetectorWithOptions:faceDetectorOptions];
UIImage *staticImg = [UIImage imageNamed:#"sample.jpg"];
FIRVisionImage *visionImage = [[FIRVisionImage alloc] initWithImage:staticImg];
NSError* error = Nil;
NSArray<FIRVisionFace *> * faces = [faceDetector resultsInImage:visionImage error:&error];
NSLog(#"Synchronous result. error = %#, face count = %lu", error, faces.count);
The sample.jpg file is the following image downloaded and added as a resource to my Xcode project:
http://chwb.org/wp-content/uploads/2014/01/Theo_Janssen-Face1.jpg
The resultsInImage returns no error, but no faces either. It logs:
Synchronous result. error = (null), face count = 0
Am I doing something wrong?
I figured it out. The problem was I need to set the image metadata with orientation like this:
FIRVisionImageMetadata *imageMetadata = [FIRVisionImageMetadata new];
imageMetadata.orientation = [FcFaceDetector visionImageOrientationFromImageOrientation:uiImage.imageOrientation];
visionImage.metadata = imageMetadata;
+ (FIRVisionDetectorImageOrientation) visionImageOrientationFromImageOrientation:(UIImageOrientation)imageOrientation {
switch (imageOrientation) {
case UIImageOrientationUp:
return FIRVisionDetectorImageOrientationTopLeft;
case UIImageOrientationDown:
return FIRVisionDetectorImageOrientationBottomRight;
case UIImageOrientationLeft:
return FIRVisionDetectorImageOrientationLeftBottom;
case UIImageOrientationRight:
return FIRVisionDetectorImageOrientationRightTop;
case UIImageOrientationUpMirrored:
return FIRVisionDetectorImageOrientationTopRight;
case UIImageOrientationDownMirrored:
return FIRVisionDetectorImageOrientationBottomLeft;
case UIImageOrientationLeftMirrored:
return FIRVisionDetectorImageOrientationLeftTop;
case UIImageOrientationRightMirrored:
return FIRVisionDetectorImageOrientationRightBottom;
}
}
The docs seem to be unclear about it, because it seems to suggest to not set it:
https://firebase.google.com/docs/ml-kit/ios/detect-faces#2-run-the-face-detector

Add itemEditorValidatorFunction with Pop up window confirmation to Flexicious Grid

I am trying to have my Flexicious DataGrid ask for confirmation of a change when I click in a cell to edit a value and enter a new value which deviates from the original by a certain percentage. I cannot see an easy way to do this. Initially, I tried to write a itemEditorValidatorFunction, which returns a boolean. This works perfectly for a hard coded return value, but if I try to take the return value from the CloseEvent of an Alert, that value is ignored:
protected function validateGcCap(editor:UIComponent):Boolean{
var warningBPDiffVal:Number = Number(5);
var warningPerCentDiffVal:Number = Number(warningBPDiffVal / 1000);
var allowChange:Boolean = true;
var origGcCapVal:Number = Number(managerGrid.getCurrentEditingCell().text);
var newGcCapVal:Number = Number((editor as TextInput).text);
var diffVal:Number = Number(newGcCapVal - origGcCapVal);
if (origGcCapVal > newGcCapVal) {
diffVal = origGcCapVal - newGcCapVal;
}
if (diffVal > warningPerCentDiffVal) {
//Alert.show("you changed the gccap from " + origGcCapVal + " to " + newGcCapVal + " by " + diffVal);
function alertCloseHandler(event:CloseEvent):void{
if (event.detail == Alert.CANCEL) {
allowChange = false;
}
};
var alert:Alert = Alert.show("Are you sure that you want to update gcCap% by more than " + warningBPDiffVal + "bps?",
"Please Confirm", (Alert.OK | Alert.CANCEL),
this, alertCloseHandler);
}
return allowChange;
}
I also tried to write a itemEditor for the grids:FlexDataGridColumn, where I extended com.flexicious.controls.TextInput, but I could not work out which method to override. I wanted to override the method and only make the call to super if the Alert was clicked OK, but I could not see which method I should override. I tried override protected function onTextInput(textEvent:TextEvent):void, but this did nothing.
I would be grateful for any insight into this problem.
Not sure why someone decided to downvote your question, it seems quite valid. From looking at this, the best way for you would be to "undo" the edit when the user selects no on the box. If you have enableTrackChanges on, all you have to do is to remove that change from the dgGrid.changes collection and call dgGrid.refreshCells(). If you dont have enableTrackChanges, all you need to do is to update the dataProvider row with the old value, call dgGrid.refreshCells() and you should be set.
This is what works:
private function validateGcCap(editor:UIComponent):Boolean{
var warningBPDiffVal:Number = Number(5);
var cell:IFlexDataGridCell = managerGrid.getCurrentEditingCell();
var warningPerCentDiffVal:Number = Number(warningBPDiffVal / 1000);
var origGcCapVal:Number = Number(cell.text);
var newGcCapVal:Number = Number((editor as TextInput).text);
var diffVal:Number = Number(newGcCapVal - origGcCapVal);
if (origGcCapVal > newGcCapVal){
diffVal = origGcCapVal - newGcCapVal;
}
if (diffVal > warningPerCentDiffVal){
function alertCloseHandler(event:CloseEvent):void{
if (event.detail == Alert.CANCEL) {
IAParamsVO(cell.rowInfo.data).gcCapWrapper = origGcCapVal;
managerGrid.refreshCells();
}
}
Alert.show("Are you sure that you want to update gcCap% by more than "
+ warningBPDiffVal + "bps?", "Please Confirm", (Alert.OK | Alert.CANCEL),
this, alertCloseHandler);
}
return true;
}

Unsufficient privileges from responseText in Plone4.3

I use PloneBooking3.0.0a2 with Plone4.3.3, but if I want to show periodic bookings I get an unsufficient privileges error. In my opinion there are two functions responsible for that:
function showPeriodicityResult(url, alt_url, target_id, form_id, waiting_text) {
ajaxobject = getXmlHttpRequest();
form = document.getElementById(form_id);
periodicity_type = getPeriodicityType(form);
periodicity_end_date = form['periodicity_form_periodicity_end_date_0'].value;
periodicity_variable = form['periodicity2_x'].value;
query = getPeriodicityQuery(periodicity_type, periodicity_end_date, periodicity_variable);
url = url + query + "&d=" + (new Date()).getTime();
alt_url = alt_url + query;
// Opera does not support ajax
if (ajaxobject == null) {
window.location = alt_url;
} else {
var node = document.getElementById(target_id);
node.innerHTML = waiting_text;
ajaxobject.open('GET', url, true);
ajaxobject.onreadystatechange = function(){CallBackGenerateAjaxHTML(ajaxobject, target_id);};
ajaxobject.send(null);
}
}
and
function CallBackGenerateAjaxHTML(ajaxobject, target_id) {
if (ajaxobject.readyState == 4) {
if (ajaxobject.status > 299 || ajaxobject.status < 200) {
return;
}
elem = document.getElementById(target_id);
elem.innerHTML = ajaxobject.responseText;
}
}
Especially the innerHTML setting with responseText seems to be a problem. Is there is a quick answer like Plone version diff from 3 to 4 or must I work in-depth?
You mentioned in the comments that the portal.uid_catalog raises the Unauthorized.
When I recall correctly the uid-catalog requires a higher permission since the last Plone hotfix. But you also can search an Item when given a UID with the normal Catalog.
here_obj python:portal.portal_catalog(UID=here_uid)[0].getObject();
This way you should be able to get your Object.

How do you use reactive Sessions with pass-by-reference items? (Arrays, objects, etc.)

I'm making a simple function like this:
Game.msg = function(msg){
var m = Session.get("messages") || [];
m.push({"text": msg});
Session.set("messages", m);
};
and a template:
Template.field.messages = function(){
return Session.get("messages");
};
Triggering Game.msg() doesn't trigger an auto-update of the template. I suspect it's because the Array reference hasn't changed [even though the contents have]. What's the best way to trigger an update?
My hacky workaround is to have a dummy count variable (var c = Session.get("message_count")) which I set in Game.msg and reference in Template.field.messages, like this:
Game.msg = function(msg){
var m = Session.get("messages") || [];
m.push({"text": msg});
// silly, but adding a count so the array size changes and triggers a flush
Session.set("messages", m);
Session.set("message_count", m.length);
};
Template.field.messages = function(){
var c = Session.get("message_count");
return Session.get("messages");
};
How about using _.extend to create a new mutable object like this?
Game.msg = function(msg){
var m = Session.get("messages");
m = _.extend([], m);
m.push({"text": msg});
Session.set("messages", m);
};
I think it's a little bit clear than having a new variable in Session.
P.S. sorry, I have not enough reputation to comment, so I turn it into an answer.

Flex Newbie XMLList question - Sorting XML and XMLList

Is it possible to sort an XMLList? All the examples I can find on it create a new XMLListCollection like this:
MyXMLListCol = new XMLListCollection(MyXMLList);
I don't think the XMLListCollection in this case has any reference to the XMLList so sorting it would leave my XMLList unsorted, is this correct?
How can I sort the XMLList directly?
Thanks
~Mike
So I finally got my search terms altered enough I actually churned up an answer to this.
Using the technique I got from here:
http://freerpad.blogspot.com/2007/07/more-hierarchical-sorting-e4x-xml-for.html
I was able to come up with this:
public function sortXMLListByAttribute(parentNode:XML,xList:XMLList,attr:String):void{
//attr values must be ints
var xListItems:int = xList.length();
if(xListItems !=0){
var sortingArray:Array = new Array();
var sortAttr:Number = new Number();
for each (var item:XML in xList){
sortAttr = Number(item.attribute(attr));
if(sortingArray.indexOf(sortAttr)==-1){
sortingArray.push(sortAttr);
}
//piggy back the removal, just have to remove all of one localName without touching items of other localNames
delete parentNode.child(item.localName())[0];
}
if( sortingArray.length > 1 ) {
sortingArray.sort(Array.NUMERIC);
}
var sortedList:XMLList = new XMLList();
for each(var sortedAttr:Number in sortingArray){
for each (var item2:XML in xList){
var tempVar:Number = Number(item2.attribute(attr));
if(tempVar == sortedAttr){
sortedList += item2
}
}
}
for each(var item3:XML in sortedList){
parentNode.appendChild(item3);
}
}
}
Works pretty fast and keeps my original XML variable updated. I know I may be reinventing the wheel just to not use an XMLListCollection, but I think the ability to sort XML and XMLLists can be pretty important
While there is no native equivalent to the Array.sortOn function, it is trivial enough to implement your own sorting algorithm:
// Bubble sort.
// always initialize variables -- it save memory.
var ordered:Boolean = false;
var l:int = xmlList.length();
var i:int = 0;
var curr:XML = null;
var plus:XML = null;
while( !ordered )
{
// Assume that the order is correct
ordered = true;
for( i = 0; i < l; i++ )
{
curr = xmlList[ i ];
plus = xmlList[ i + 1 ];
// If the order is incorrect, swap and set ordered to false.
if( Number( curr.#order ) < Number( plus.#order ) )
{
xmlList[ i ] = plus;
xmlList[ i + 1 ] = curr;
ordered = false;
}
}
}
but, realistically, it is far easier and less buggy to use XMLListCollection. Further, if someone else is reading your code, they will find it easier to understand. Please do yourself a favor and avoid re-inventing the wheel on this.

Resources