I was wondering if there was any option to search an element by its id but not knowing the full ID, only part of it. So I could find an element without knowing its full ID or find multiple elements with similar IDs.
For example if I knew I had 3 objects with the followings ID:
"objectID1" "objectID2" and "objectID3".
Could I something like:
getElementByID("objectID*")
I have tried it in JavaScript using: input[id*='PART_OF_ID_I_KNOW']
But it returns an HTML object and I need it for SAPUI5.
Could I use something like:
var myControl = sap.ui.getCore().byId('myId');
But not having to match the full ID (myID)? Thanks.
Though I would not recommend this but it's possible in a way as you describe it.You could look for elements with similar ID with jQuery, get the element's ID and pass it to sap.ui.getCore().byId();
var aElements = $("div[id*='PART_OF_ID_YOU_KNOW']");
//Lets say the first element returned is the one belonging to your control
var oControl = sap.ui.getCore().byId(aElements[0].id); //If the element is a SAPUI5 control, you should get it.
Why do you need to do this? Is it because you want to access controls (with prefixed IDs) inside your views and fragments? Did you give an ID of "myControl" to the control, but sap.ui.getCore().byId("myControl") doesn't work as the framework added a prefix to it?
If yes, the only reliable way to get a reference to your control is by using the framework provided methods in MVC views and controllers and in fragments.
If you have a control called "myButton" in your view, do this.byId("myButton") or this.getView().byId("myButton") from the controller to get a reference to your control.
If you have a control called "myButton" in a fragment that you embedded in your view via sap.ui.xmlfragment("", "myFragment.fragment.xml"), then use sap.ui.core.Fragment.byId("<prefix>", "myButton") to access it.
Whatever you do, don't make assumptions on how the framework creates these prefixed IDs. These are not documented and can change.
when you use `var myControl = sap.ui.getCore().byId('myId');`
it won't work.It is because when you try to get control by sap.ui.getCore() sapui5 automatically concat extra string to Your id egsap.ui.getCore().byId('xml0--myId') and if you have provided viewId in manifest then while rendering control it uses that. eg
sap.ui.getCore().byId('yourManifiestId--myId')
Related
I do have a XML-Model which looks like this:
I would like to add the sap.m.ComboBox control to my UI. I want the value from attribute Name from the Member tag. I am able to do so with this code:
new sap.m.ComboBox({
items : {
templateShareable : true,
path : "metadata>/edmx:DataServices/edm:Schema/edm:EnumType/0/edm:Member",
template : new sap.ui.core.ListItem({
text: "{metadata>#Name}"
})
}
})
BUT, instead of selecting the EnumType hard by calling it's index (edm:EnumType/0/), I would rather like to select it by it's attribute Name. E.g. something like this would be nice:
"metadata>/edmx:DataServices/edm:Schema/edm:EnumType(Name=RoleCategory)/edm:Member"
Does anyone know how to do so? Any idea is highly appreciated.
There is no such thing in the path syntax. You can see in the OpenUI5 code that the path supports only
attributes #
text()
elements by tag name
array indices.
You cannot use element binding to filter either as element binding does not support filtering and sorting.
You could however attach to the models requestCompleted or metadataLoaded events and update the binding path or copy the data to a separate model.
If you want it dirty you could use a container control, bind it to /edmx:DataServices/edm:Schema/edm:EnumType with your ComboBox as template and apply an appropiate filter. You then have to use a relative path in you Combobox. :)
Suppose I have a div tag like this:
<div id="group-dialog" class="modal-dialog">
Now I want to grab it as a jQuery object (in this case so I can run .dialog()).
When I try this:
var gDialog = $('#group-dialog');
I get an array back (!!).
Why am I getting an array? Isn't the point of having an ID attribute that there's only one? I can see getting multiple p's or .my-css-thing back ...
Next question:
I have this array with 1 object in it that I now want to access as a jQuery object.
When I do this:
$(gDialog[0])
And pull it up in F12, I still have an array!! I thought I de-referenced the array already by picking the first element.
This doesn't seem to help either:
var gDialog = $('#group-dialog:first');
This is basic, but I run into this problem a lot. It seems like it used to be a lot simpler!
What is the best way to access this DOM element as a jQuery object?
Answer 1
jQuery selectors always return arrays.
Selection with id attribute is a particular use case and ideally the result should be unique. However, there is nothing preventing you from having duplicated ids in a HTML document (although this is bad practice).
Answer 2
The following code will get you the first element as a DOM object:
var gDialog = $('#group-dialog')[0];
Note: you may want to check the size of the return array first.
As far as I know, there is no way to transform this DOM element back to a jQuery object. The standard use case would be to directly used $('#group-dialog') and asume that it is found and unique.
Try using .get(). Though I'm not sure it will work with dialog()
Retrieve the DOM elements matched by the jQuery object.
var gDialog = $('#group-dialog').get();
If you're trying to grab it to use it on a dialog, you can just put
$(document).ready(function(){
$('#group-dialog').dialog({put options here})
});
I hope I can expain myself what I mean.
Let's say I have a car resource. The car has the attributes color, name or whatever.
I get the list of cars using a service, something like cars.index().
But in the interface I have all the cars and when I click on one car, a little popup appears showing the inputs to edit the color and the name.
And here comes the issue. Where do I save the displayingInputs attribute?
Should I save it directly in the car resource and then just send the original attributes when submitting to the updated resource?
Should I create a new service called carWidget or something along the lines that each one has something like:
{
car: cars.get(carId),
displayingInputs: false
}
Should I store the displayingInputs inside a carWidget directive scope? What happens if I need to change the `displayingInputs from the parent scope? (for example when making a "display all"/"hide all" button)
Something else?
My best bet is #3, but I'm not sure how should I access the displayingInputs from outside the widget.
If you want to keep your car model clean, you can have a separate variable editedCar and display each popup with ng-show="car == editedCar".
If multiple cars can be edited at the same time, editedCars can be an associative array (car ID => boolean) and display popups using ng-show="editedCars[car.id]".
Another way not to send certain car properties is to prefix their name with a $ sign. This was simply use car.$displayingInputs. Be careful for name collisions as Angular uses this prefix to store internal data.
From the angular.toJson doc:
Serializes input into a JSON-formatted string. Properties with leading
$ characters will be stripped since angular uses this notation
internally.
I have a question about best practices when using jQuery/JavaScript/Ajax. Lets say that I have some tasks and there is a calendar for every task. The User is able to click on a day in a task calendar and book the task at the specific day via AJAX. I have to store the date and the ID of the task somewhere and i am using really bizarre IDs for that such as:
<span class="day_field" id="date_13-02-2013_task_4">13.02.2013</span>
Then i just attach an listener like this:
$('.day_field').on('click',function(){
var date = $(this).id.split('_')[1];
var task_id = $(this).id.split('_')[3];
//place for some validation
$.post('book_task.php',{task_id: task_id, date: date},function(data){
//something cool with the result
});
});
My question is: Is this the right way how to do it? I am not pretty sure, because the IDs can be really long + it contains ID in database which is not probably save at all.
Thanks!
T.
Use HTML5 data attributes:
<span class="day_field" data-date="13-02-2013" data-task="4">13.02.2013</span>
$('.day_field').on('click',function(){
var date = $(this).data("date");
var task_id = $(this).data("task");
//place for some validation
$.post('book_task.php',{task_id: task_id, date: date},function(data){
//something cool with the result
});
});
The right wayA better way to do it would be to store the data in either data attributes, or make the span an anchor tag and store the param string desired in the href attribute.
<span class="day_field" data-date="13-02-2013" data-task="4>13.02.2013</span>
or
<a class="day-field" href="?task_id=4&date=13-02-2013">13.02.2013</a>
with this for the anchor tag:
$('.day_field').on('click',function(e){
e.preventDefault();
$.post("foo.php",this.href,handler);
});
Instead of an ID, you can use custom data attributes, like this:
<span class="day_field" data-date="date_13-02-2013_task_4">13.02.2013</span>
And then you can access the value like this in jQuery:
$(".day_field").data("date");
Exposing the actual ID of something in your database is only as insecure as your database.
Using the id of the element seems fine to me, too, if it uniquely identifies a thing. Using the data attributes is a possibility to save on splitting logic if you like, but you could still use id in tandem.
Conventionally speaking, this is very tame code compared to much of what jQuery is.
One more elegant way to associate data to an element is to use jQuery's data. However, I would consider building a jQuery plugin and using one instance of it for each task. A plugin encapsulates all of the data it needs, so you wouldn't need to store it tied to the element, which is not great.
I will first explain what I'm trying to do then I will explain why just in case you get bored of reading the whole scenario.
Basically I have some HTML markup stored in a variable I now need to a wait to access the different elements within the variable. For example:
var markUp = "<h3>h3 tag</h3><p>paragraph tag</p>";
What I need to know is if there is a way for me to query the variable to retrieve say the h3 tag, in a similar way you would use the query function ? I have seen some other practices where people append the var to a hidden div then query the div. I would prefer to avoid this but if that is the only way I will proceed.
I have come across this problem whilst developing a drag and drop application, on drop i use a custom creator function to change the items structure once it is dropped.
If further explanation is needed please say, thanks advance Jonathan
You can use dojo._toDom to create a DOM fragment from your string.
var markup = "<h3>h3 tag</h3><p>paragraph tag</p><p>another paragraph</p>";
var domFragment = dojo._toDom(markup);
dojo.query("p", domFragment).forEach(function(element,i) {
console.debug(element.innerHTML);
});
The underscore prefix in _toDom means that it's a "private" member method of dojo. Normally, it's bad practice to use these as if they were public (like I do here). However, in the case of _toDom I believe it's generally considered acceptable, and according to this trac entry, it sounds like it'll be made public in the next version.