I am attempting to build a small proof-of-concept web application using the web2py framework. I'm so close, but my basic lack of knowledge of what's going on means I'm just hacking at it with pure guesswork rather than understanding what's going on. I was hoping someone on here could explain where I am going wrong...
The functionality I'm after is that the data needed to create the draggable items is held in a database table (and will ultimately form a hierarchy) with as little information held in the HTML as possible.
There's a fair bit of information for just about everything in this stack, so much so that I'm drowning in it, I don't know where to start. I suppose I should begin with what I've got so far...
The HTML:
<script src="//code.jquery.com/jquery-1.10.2.js"></script>
<script src="//code.jquery.com/ui/1.11.2/jquery-ui.js"></script>
...
<script>
$(document).ready(function(){
$.ajax( {
type: "POST",
url: 'dragndrop.py',
success: function( response ) {
$("#draggable7").html(response);
}
} )
});
</script>
<div id="draggable7"></div>
The dragndrop.py script:
## My main draggable spawner
selected = [row.id for row in db(db.t_user_shop_layouts.id==7).select()]
return ''.join([DIV('draggable'.join(k), _class='draggable ui-widget-content', _snap=".ui-widget-header", _snapMode= "inner", _grid= [ 80, 80 ], _style='position: relative;') for k in selected])
And, just for completeness, the model web2py script (although the column I'm interested in is the "id" column, which is auto-generated):
db.define_table('t_shop_layout_items',
Field('f_item_display_name_string', type='string', notnull=True,
label=T('Item Display Name String')),
Field('f_item_icon_file', type='upload',
label=T('Item Icon File')),
Field('f_item_parent_id', type='integer',
label=T('Item Parent Id')),
auth.signature,
format='%(f_item_display_name_string)s',
migrate=settings.migrate)
I'm forcing the db call to only pick up one row at the moment (id == 7) just to get the ball rolling, but eventually what I'd like to do is have the (db.id == db.f_item_parent_id) items shown first. Then when double-click, any (db.f_item_parent_id == this.id) children get spawned using helpers. Then I'm going to get an 80x80 grid size target to land on to set shop layout, and save to db. But all this paragraph is for later, I'm just giving you an idea of where I'm going with it.
Finally, some great tutorials that have helped me along the way, but were either not web2py (PHP seems popular for this) or not dynamically spawning (but hard-coded in the HTML, or what-have-you. If I've missed something obvious, please let me know:
An excellent fiddle: http://jsfiddle.net/robertrozas/qLhke/25/ and its stack overflow beginnings Jquery drag drop form hidden value inserting into php mysql
The web2py documentation: http://web2py.com/books/default/chapter/34/11/jquery-and-ajax
OK, hope that's enough! Any help would be appreciated!
In web2py, you do not create .py files and then use them as URLs. Instead, you create functions in controllers and have URLs of the form /appname/controller/function. See the documentation on dispatching. It is also best to use the built-in URL() function to generate URLs. Also, this should probably be a GET request rather than POST.
You might also want to look into web2py's built-in ajax() function as well as Ajax components.
Regarding your data model, if the f_item_parent_id field is a self reference, then you should define it as a reference field (i.e., type='reference t_shop_layout_items').
More generally, before proceeding further, it will probably be very helpful if you read more of the documentation, particularly chapters 4, 5, 11, and possibly 12.
Related
I am building an ember app and it is starting to get large. Is there any way to do lazy loading of the ember files so that it does take 10+ seconds to load when the user first hits the site? For example since I have several logically separate modules as part of the site, I could load the modules as they are accessed. I am using ruby on rails and the ember-rails gem.
If you think about what Ember is actually doing to render that code, you can understand why it is slow. Suppose you're creating 2k view instances, and rendering 2k templates. Templates that for the most part are doing very little. Especially if you don't care about data binding.
For a first stab, let's stop rendering through templates. This code uses itemViewClass to render each item with a custom view instead of the view used internally by each.
// Use with {{each item in items itemViewClass=App.SpanView}}
App.SpanView = Em.View.extend({
render: function(buffer) {
buffer.push("<span>"+this.get('content')+"</span>\n");
}
});
JSBin: http://jsbin.com/enapec/35/edit66
With render over-ridden, we need to interact with the render buffer ourselves.
Even faster would be getting rid of the view entirely. I think there are two ways to do this. You could create a custom view with a render method that loops over all the items, and pushes each element onto the buffer. I think given the previous example you can get that going yourself.
Another simple option is to use a helper. A dumb helper like this is more difficult to wire up for re-rendering when the list changes, but sometimes it is the right solution.
// Use with {{eachInSpan items}}
Em.Handlebars.registerBoundHelper('eachInSpan', function (items) {
return (
new Handlebars.SafeString(
items.map(function (i) {
return '<span>'+i+'</span>';
})
)
);
});
Live JSBin: http://jsbin.com/enapec/34/edit
Lastly, you could do this in jQuery with didInsertElement and the afterRender queue. I don't recommend it though.
Ember.RenderBuffer gathers information regarding the a view and generates the final representation. Ember.RenderBuffer will generate HTML which can be pushed to the DOM.
FYI here is the RenderBuffer API
DEFINED IN
MODULE : Ember-views
I am also new bee but I got this from some resource. Thanks.
On this Keynote on Embercamp London 2016, #wycats and #tomdale talk about the plans for improving Ember with slicing and dicing of the app. They talk about loading only what it's needed for that particular route. This is going to be great. I think that's what you wanted :)
https://www.periscope.tv/w/1mrGmzPBvQqJy#
I know there are many tutorials but they concentrate on xul, and manipulating menus and examples are overcrowded with features.
What I need is a simple extension that will for example add a red border to all <body> elements of every page I'm visiting and js would show me alert when a page is finished loading. Just to show that it is working and I will have a point to start learning from.
I know that there are ready extensions like greasemonkey and user css but what I intend to do is to first make such functionality raw, without overhead of yet another extension. And second to have ha proof of concept code so I can learn other features of firefox api.
I know how to write chrome/opera extension. I know all the languages needed, and how to make a mock extension, so it show up in firefox addons list. Vut the problem is that I don't know what to put where to get to the content of actual web page.
I know that there is a file called main.js that I'm supposed to put somewhere with code like this:
var data = require("self").data;
var pageMod = require("page-mod");
pageMod.PageMod({
include: "*",
contentScriptFile: data.url("my_script.js"),
contentStyleFile: data.url("my_style.css")
});
And that begin to look familiar, like in Chrome., my script code:
window.addEventListener("load", function() {
alert("hello there!");
}, true);
But I don't know where to put these files. Are there some default location, or must I set some configuration file to let know the api where main.js is ?
I know that there are projects to make such css/js based extension simpler, like jetpack - but that still creates overhead. I want to learn, but also don't waste my time and create something useful while doing that based on the knowlegde I have from chrome API.
edit:
I found this tutorial: https://developer.mozilla.org/en-US/Add-ons/SDK/Guides/Content_Scripts/Accessing_the_DOM - but there is nothing on where to put these files there is no example extension using these features.
edit2: https://github.com/mozilla/addon-sdk/tree/master/examples - there is no link for these in mozdev examples, one must search this thru google
Are you still in need of a ready made example?
Here is a bootstrap addon template that does exactly this. You just need to edit the addDiv and removeDiv functions for starters.
https://gist.github.com/Noitidart/9287185
It's called the Add-on SDK. Start here
I'm currently struggling with the problem of multilingualism in an SPA.
I've come up with several solutions, like building a wrapper for the resources resx files, or saving all labels in the database, but I am wondering if any of you have found some solution which automates these steps.
Are there any practices which are specific for this problem?
For a reasonable amount of literals, I suggest to save the resources in the DB or in a .RESX file in the server. When the user logs in or you detect the language that will be used, the literals are requested by the application and saved either in a collection of your translation module or in the LocalStorage of the browser (this could be a good approach for large data).
Then this module could have some methods to retrieve the messages, probably passing a key.
Using this solution you could inject this module in the viewmodels that need to show translated literals and acces them through the view:
<p data-bind="text: resourceManager.get('M01')"></a>
For large applications that would require huge localization data to be transfered, maybe some kind of modularity could be applied and only load the resources really needed for each module/section.
I don't think making recurrent requests to the server to get the translated literals is a good practise. SPA's should provide a good user experience and loading the translated literals from the server could be a blocking issue. Text is not like an image, you can render a page without all the images loaded, imagine rendering a page without the text :o
Anyway, I think the best solution would be to keep the server as repository and create a custom JS module that takes care to get data in one or multiple loads and is able to store it somewhere in the client.
I've solved my own problem, using a custom binding and i18next.
First, I've implemented i18next for translation of my labels/buttons and other resources.
Secondly, I've added a custom Knockout bindingHandler:
ko.bindingHandlers.i18n = {
init: function (element, valueAccessor) {
var translateKey = valueAccessor();
ko.utils.setTextContent(element, $.t(translateKey));
}
};
Finally you can add the following code to your views:
<span data-bind="i18n : 'buttons.cancel'"></span>
This will automatically get the correct resource, and Knockout will handle the bindings.
Hopefully this will help others struggling with the same problem.
I'm using Rails 3 to create a project that will need a model called Sketch. I've already created a model, controller, and migration to handle Sketch - so far it just creates a 'sketch' object with a name for each sketch.
My problem is that I need to be able to attach an html5 canvas to each sketch object when it is created (or remove it when it is destroyed).
Since 'canvas' is not a datatype that will be stored in the database (like 'string', 'integer', or 'datetime'), how do I go about creating custom html components such as this that need to be treated like any other datatype in a Rails app?
I'm assuming that you would need to add the html components to a Model method and use a callback - like after_save - to initiate the component. But I'm not sure at all how to do this.
Not sure if I'm describing this well enough, so here is a very simple mockup:
I have the Raphael Javascript library in mind for the component that will do the sketching - if that helps.
If you can point me to any tutorials on this subject that would be great.
HTML5 canvases are rendered in the browser, not on the server where your ruby code is actually executed. Therefore I think it's safe to say that what you're asking isn't possible (at least in the way the question is phrased).
Instead you'll need to work with HTML, CSS and Javascript in your view to get the canvas working.
Canvas Tutorial / Reference
Hope this helps.
(On a related note, it's also considered a bad practice to mix view-related concepts in with your models.)
I am trying to build a simple jQuery UI template and populate it with data stored in the localStorage.
I need to set the local storage with a list of guests and have the user edit the list. When clicking update, the changes are sent back to the server.
<ul id="guests">
<li>
Name: ${name} <br />
Phone: ${phone} <br />
Email: ${email}
</li>
</ul>
I am really new at this and have no idea what to do. I am just interested in setting the local storage when the page loads and populating the template.
Can someone please provide a short tutorial?
I thought this is a simple question... Can someone please let me know in case it is not possible at all? Thanks!
you say you want to save the data to localStorage, but also that you want to send modified data to the server.
I would suggest that you divide this problem up into (Part 1) learning how to save locally to localStorage and rendering that content with templating and then (Part 2) learning how to store on a server. I can help you with Part 1, since quite frankly I'm still learning about Part 2 myself.
Okay so, two subtasks:
using localStorage to persist data
using jQuery templates to render data
Using localStorage
You haven't specified where your data is coming from, so I'll assume you have some JSON. For simplicity I'll just use this data:
(You might be wondering why I added content that isn't plain ASCII -- it's just a habit of mine, I believe in testing with realistic text from the get-go. When we finally render this data, it should look right in your browser.)
var philosophers = [
{
"phone": "1-800-123-1937",
"name": "H\u00e9l\u00e8ne Cixous",
"email": "helene#stanford.edu"
},
{
"phone": "1-800-000-0000",
"name": "\u041c\u0438\u0445\u0430\u0438\u0301\u043b \u0411\u0430\u043a\u0443\u0301\u043d\u0438\u043d",
"email": "mikhail#ispitondns.com"
},
{
"phone": "1-800-770-0830",
"name": "Jayar\u0101\u015bi Bha\u1e6d\u1e6da",
"email": "jay#ancientindia.edu"
}
]
So we need to get this into localStorage, just to have some data to start with.
The trick about localStorage is that you can't just directly store JSON objects. You can only store strings. There are some libraries out there designed to improve on this situation, but we'll just convert our objects ourselves. To do that we'll use JSON:
localStorage.philosophers = JSON.stringify(philosophers)
Unsurprisingly, JSON.stringify turns JSON objects into a string, and that can be set directly as an "attribute" of localStorage.
(If you're using an old browser, then you might not have the native JSON object -- there's a library you can include for that too.)
Okay, so now we have some contact data stashed in localStorage with the label of philosophers. (Hey, you never know when you might need to call a philosopher!)
To get that data back out and into a Javascript object we can do something with, we use another JSON method, JSON.parse.
philosophers = JSON.parse(localStorage.philosophers)
This is all pretty artificial, since we've got the philosophers data in the first place, then we stringify it, and then we store it, and then we take it right back out, and then we parse it, and then we're back where we started. But in reality such data will come from some other source -- perhaps an external file or a web service or whatever.
Using templates to render objects
Since you used what looks like jQuery template syntax in your template, I'm going to assume that's the library you're using. The jQuery docs show us how we can render a variable containing some objects (like what we have in our philosophers variable) with a template, here's the key bit of those docs:
// Convert the markup string into a named template
$.template( "summaryTemplate", "<li>${Name}</li>" );
function renderList() {
// Render the movies data using the named template: "summaryTemplate"
$.tmpl( "summaryTemplate", movies ).appendTo( "#moviesList" );
}
Here's one way you can get your template to work (there are other, arguably cleaner methods, but jQuery templates are a topic unto themselves):
var myTemplate = "<li>Name: ${name}<br/>Phone: ${phone}<br/>Email: ${email}</li>";
$.template("contactLi", myTemplate);
That creates a template and stores it in a variable named contentLi. (Note that $.template wants that given variable name given as a string, which strikes me as weird. I find the way jQuery templates names and defines these methods confusing, which is one of the reasons I prefer Mustache for templating. Shrug.)
Also, note that we don't have the ul included in the template, because that's not going to be repeated for each rendered object. Rather, we're going to add the ul as a hook in the markup, and render the assembled template repeatedly as a child of that. Which just takes a single line with jQuery templates, rather nice:
$.tmpl( "contactLi", philosophers ).appendTo( "#guests" );
So there you go, a rendered list.
I know this doesn't answer your whole question but there's a lot here to start with.
Here's an example you can try out, it ends up rendering something like:
Name: Hélène Cixous
Phone: 1-800-123-1937
Email: helene#stanford.edu
Name: Михаи́л Баку́нин
Phone: 1-800-000-0000
Email: mikhail#ispitondns.com
Name: Jayarāśi Bhaṭṭa
Phone: 1-800-770-0830
Email: jay#ancientindia.edu
(Hehe, boy, SO's syntax highlighting doesn't handle that Unicode text very well!)
try AmplifyJS -- can extract your data as json the same way you would as $.getJSON