I have two QListWidgets. I want to be able to move items from widget 1 onto widget 2 and vice versa by dragging and dropping. It must work with MultiSelection mode. It must be a MoveAction NOT a copy action. A simple way to achieve this is to use:
self.listWidget_2.setDragDropMode(QtWidgets.QAbstractItemView.DragDrop)
self.listWidget_2.setDefaultDropAction(QtCore.Qt.MoveAction)
self.listWidget_2.setSelectionMode(QtWidgets.QAbstractItemView.MultiSelection)
self.listWidget_2.setObjectName("listWidget_2")
self.listWidget_2.acceptDrops()
This achieves all the desired requirements with one caveat. Dragging and dropping the item onto the widget where it currently resides removes it from the widget. A definite no go. I Then tried to write my own QListWidget class to achieve my desired results to no avail, this is the class:
class dragLeaveList(QtWidgets.QListWidget):
def __init__(self, type, parent=None):
super(dragLeaveList, self).__init__(parent)
self.setDragDropMode(QtWidgets.QAbstractItemView.DragDrop)
self.setSelectionMode(QtWidgets.QAbstractItemView.MultiSelection)
self.setAlternatingRowColors(True)
self.setAcceptDrops(True)
def dragEnterEvent(self, event):
if event.mimeData().hasText():
event.accept()
print("Drag Enter Event: IF CLAUSE")
else:
super(dragLeaveList, self).dragEnterEvent(event)
print("Drag Enter Event: ELSE CLAUSE")
def dragMoveEvent(self, event):
if event.mimeData().hasText():
event.setDropAction(QtCore.Qt.MoveAction)
event.accept()
else:
event.ignore()
super(dragLeaveList, self).dragMoveEvent(event)
def dropEvent(self, event):
print("Drop Event ", event)
if event.mimeData().hasText():
event.setDropAction(QtCore.Qt.MoveAction)
event.accept()
print("Drop Event - 1 ", event)
def startDrag(self, event):
print("In Start Drag")
item = self.currentItem()
itemText = self.currentItem().text()
itemData = QtCore.QByteArray()
dataStream = QtCore.QDataStream(itemData, QtCore.QIODevice.WriteOnly)
print(item, itemText)
mimeData = QtCore.QMimeData()
mimeData.setData(itemText, itemData)
drag = QtGui.QDrag(self)
drag.setMimeData(mimeData)
if drag.exec_(QtCore.Qt.MoveAction) == QtCore.Qt.MoveAction:
if self.currentItem() is not None:
self.takeItem(self.row(item))
I've read every tutorial online and all the related documentation on sourceforge and i just can't seem to make this work. I rarely end up not being able to figure something out but the documentation for this just seems to be pretty darn bad. I'm really looking for explanations along with the code. However, as i said I've read all the related documentation multiple times so I'm not completely ignorant. Seems to me in the above class that i have a lot more then what i need and it may have the right components just not the right implementation. Please give me some clarity on this subject, thanks a bunch.
Main things to clarify in answer code
The bare minimum/most effective DragDrop(the built in methods i.e. dragEnterEvent, dragMoveEvent et cetera) methods.
Is mimeData() absolutely required? Assume yes from the Docs.
Formatting the mimeData() into a QListWidgetItem.
Does the item have to be manually removed from the widget or is this
built in with the QtCore.Qt.MoveAction?
Actually making the QtCore.Qt.MoveAction move the list item.
So i have figured out one solution to get everything in working order. Keep in mind that this answer does not teach me what i wanted to know. However, this may be helpful to others wishing to do something the same or similar. I'm am still looking for a method the touches on the topics listed in " Main things to clarify code" list.
class QListDragAndDrop(QtWidgets.QListWidget):
def __init__(self):
super(QListDragAndDrop, self).__init__()
self.setFrameShape(QtWidgets.QFrame.WinPanel)
self.setFrameShadow(QtWidgets.QFrame.Raised)
self.setDragEnabled(True)
self.setDragDropMode(QtWidgets.QAbstractItemView.DragDrop)
self.setDefaultDropAction(QtCore.Qt.MoveAction)
self.setSelectionMode(QtWidgets.QAbstractItemView.MultiSelection)
self.setMovement(QtWidgets.QListView.Snap)
self.setProperty("isWrapping", True)
self.setWordWrap(True)
self.setSortingEnabled(True)
self.setAcceptDrops(True)
Just make this QListWidget class with these parameters set and import to wherever you need it works like a charm but does not really teach you much. Hopefully, this helps certain people get by until someone answers the question properly.
Related
This question may have a bit of philosophical aspect to it.
I have been using Deadbolt 2 (Scala) in my Play application and it works quite well.
In looking at the Restrict function definition (line 47) I noticed that it will invoke the onAuthFailure for one of the following reasons:
No user in session (no subject)
Action specified no roles.
User attempted an action for which they did not possess one or more required roles.
In my application UI, I would like to receive a different status code for each of these so that a user that is not logged in (condition 1) will be redirected to login page but condition 3 would be more gracefully handled by just a warning (since they can do no harm anyway and might have accidentally tried to edit when they have 'read-only' access - perhaps a UI bug, but logging in again is a bit draconian).
If I had to settle for just 2 status codes, however, I would want to differentiate between 1 and the other 2. I can see how this could be accomplished but would like to get other opinions on the merits of even doing this.
If I were to implement this change, it looks like I could just override the Restrict function in my own extension of the DeadboltActions trait.
I'm a little new to scala, so I'm open to additional ideas on how to best accomplish these goals.
I decided to just add the code to differentiate between condition 1 and either 2 or 3 as follows:
In MyDeadboltHandler:
class MyDeadboltHandler(dynamicResourceHandler: Option[DynamicResourceHandler] = None) extends DeadboltHandler {
...
def onAuthFailure[A](request: Request[A]): Result = {
Logger.error("authentication failure")
val json = new JsonStatus("Failed to authenticate", -1).toJson.toString
if(noUserInSession(request)){
Results.Forbidden(json).withHeaders("Access-Control-Allow-Origin" -> "*")
}
else{
Results.Unauthorized (json).withHeaders("Access-Control-Allow-Origin" -> "*")
}
}
def noUserInSession(request:RequestHeader) = {
username(request) match {
case Some(u:String) => false
case _ => true
}
}
This works well for me and does not impose upon the basic Deadbolt-2 functionality.
I'm attempting to write a Plone add-on that requires an "Add new" form. So far, I've managed to get this working very nicely using plone.directives.form.SchemaAddForm. I have the '##create-snippet' view registered in configure.zcml, and it works perfectly when I view the page normally.
However, the ultimate goal of this project is to get this add form into a TinyMCE popup window. I've created a working TinyMCE plugin for another, irrelevant portion of the add-on, and gotten that working well. However, when I try to navigate to my "##create-snippets" view in a tinyMCE window, I get:
LocationError: (Products.Five.metaclass.DirectoryResource2 object at 0x107162fd0, 'main_template')
My understanding of this issue is that, essentially, the SchemaAddForm class (or one of it's super classes, to be exact) wraps the form with the main Plone main_template when it renders the form. Since TinyMCE windows are their own, isolated little worlds, the template isn't available, and, therefore, cannot be rendered....or something like that? Please correct me if I'm way off.
What I really want to know, is if it's possible to set things up so only the form itself will render, without using the main_template? I would REALLY like to be able to take advantage of the schema-based forms (and their built-in validation), but still be able to keep everything within a TinyMCE window.
I've toyed around with creating my own ViewPageTemplateFile() template, and getting the form to render (somehow?) within it, but frankly, I have no idea how....or if that's even possible.
Please feel free to ask for more information if there's something I've omitted. I'm kinda new to this type of Plone development.
The code generating the form:
from Products.Five.browser import BrowserView
from uwosh.snippets.snippet import SnippetManager
from plone.directives.form import SchemaAddForm
import zope.interface
from plone.autoform.form import AutoExtensibleForm
import zope.schema
from plone.directives import form
import z3c
from Products.statusmessages.interfaces import IStatusMessage
_ = zope.i18nmessageid.MessageFactory(u'uwosh.snippets')
class ISnippet(form.Schema):
title = zope.schema.TextLine(
title=u'Title',
description=u'The title to associate with the snippet.',
required=True)
description = zope.schema.TextLine(
title=u'Description',
description=u'A short explanation of the snippet.',
required=True)
body = zope.schema.Text(
title=u'Body',
description=u'The actual content to be rendered on the page.',
required=True)
class SnippetForm(SchemaAddForm):
schema = ISnippet
#z3c.form.button.buttonAndHandler(_('Save'), name='save')
def handleAdd(self, action):
data, errors = self.extractData()
if errors:
self.status = self.formErrorsMessage
return
obj = self.createAndAdd(data)
if obj is not None:
# mark only as finished if we get the new object
self._finishedAdd = True
IStatusMessage(self.request).addStatusMessage(_(u"Snippet saved"), "info")
#z3c.form.button.buttonAndHandler(_(u'Cancel'), name='cancel')
def handleCancel(self, action):
IStatusMessage(self.request).addStatusMessage(_(u"Add New Snippet operation cancelled"), "info")
self.request.response.redirect(self.nextURL())
def create(self, data):
sm = SnippetManager()
#TODO:
#Include support for different folders from this form.
snippet = sm.createSnippet(data['title'], None ,data)
return snippet
def add(self, object):
#Since, for now, snippets are based upon ATDocuments, their creation is fairly staight-forward.
#So, we don't really need separate Add/Create steps.
return
def nextURL(self):
return self.context.absolute_url() + '/##create-snippet'
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
We don’t allow questions seeking recommendations for books, tools, software libraries, and more. You can edit the question so it can be answered with facts and citations.
Closed 3 years ago.
Improve this question
I would like to use d to create a RESTful web application.
What are the most actively maintained and contributed projects that are worth considering? A short comparison of these web frameworks with pluses and minuses will be nice.
My search lead me to only one project, which seems like an excellent framework:
vibe.d
Are there other projects which are minimal in nature like sinatra?
I've heard good things about vibe.d http://vibed.org/
Though, I've never personally used it because I wrote my own libraries well before vibe came out.
https://github.com/adamdruppe/misc-stuff-including-D-programming-language-web-stuff
vibe is better documented, so you might be better off going there, but here's how my libraries work:
cgi.d is the base web interface (use -version=embedded_httpd when compiling to use its own web server instead of CGI if you want), and I offer some RESTy stuff in a separate file called web.d. It depends on cgi.d, dom.d, characterencodings.d, and sha.d. You might also want database.d and mysql.d for connecting to a mysql database.
The way web.d works is you just write functions and it automatically maps them to url and formats data.
http://arsdnet.net/cgi-bin/apidemo/add-some-numbers
The source code to that portion is:
import arsd.web;
class MySite : ApiProvider {
export int addSomeNumbers(int a, int b) { return a+b; }
}
mixin FancyMain!MySite;
web.d automatically generates the form you see there, parses the url into the types given, and formats the return value into either html, json, or sometimes other things (for example, objects can be made into tables).
There is also an envelopeFormat url param that can wrap it in more json, best for machine consumption:
http://arsdnet.net/cgi-bin/apidemo/add-some-numbers?a=1&b=2&format=json&envelopeFormat=json
web.d.php in my github shows one way you can consume it, and web.d itself automatically generates javascript functions to call from the client:
MySite.addSomeNumbers(10, 20).get(function(answer) { alert("Server replied: " + answer); });
answer would be of the type returned by the D function.
If you don't want/need the automatic function wrapping, cgi.d alone gives access to the basic info and writing functions:
void requestHandler(Cgi cgi) {
// there's cgi.get["name"], cgi.post["name"], or cgi.request("name"), kinda like php
cgi.write("hello ", cgi.request("name"));
}
mixin GenericMain!requestHandler;
But yeah, most the documentation that exists for my library is just me talking about it on forums... I think once you've done one function it isn't hard to figure out, but I'm biased!
edit: copy/paste from my comment below since it is pretty relevant to really getting RESTy:
I actually did play with the idea of having urls map to objects and the verbs go through: web.d also includes an ApiObject class which goes: /obj/name -> new Obj("name"); and then calls the appropriate methods on it. So GET /obj/name calls (new Obj("name")).GET();, same for POST, PUT, etc. Then /obj/name/foo calls (new Obj("name").foo(); with the same rules as I described for functions above.
But I don't use it as much as the plain functions for one because it is still somewhat buggy.... and it is still somewhat buggy because I don't use it enough to sit down and fit it all! lol
You use it by writing an ApiObject class and then aliasing it into the ApiProvider:
import arsd.web;
class MySite : ApiProvider {
export int addSomeNumbers(int a, int b) { return a+b; }
alias MyObject obj; // new, brings in MyObject as /obj/xxx/
}
And, of course, define the object:
class MyObject : ApiObject {
CoolApi parent;
string identifier;
this(CoolApi parent, string identifier) {
this.parent = parent;
this.identifier = identifier;
/* you might also want to load any existing object from a database or something here, using the identifier string, and initialize other members */
// for now to show the example, we'll just initialize data with dummy info
data.id = 8;
data.name = "MyObject/" ~ identifier;
}
/* define some members as a child struct so we can return them later */
struct Data {
int id;
string name;
Element makeHtmlElement() {
// for automatic formatting as html
auto div = Element.make("div");
import std.conv;
div.addChild("span", to!string(id)).addClass("id");
div.appendText(" ");
div.addChild("span", name).addClass("name");
return div;
}
}
Data data;
export Data GET() {
return data;
}
export Data POST(string name) {
parent.ensureGoodPost(); // CSRF token check
data.name = name;
// normally, you'd commit the changes to the database and redirect back to GET or something like that, but since we don't have a db we'll just return the modified object
return data;
}
// property accessors for the data, if you want
export int id() {
return data.id;
}
}
mixin FancyMain!MySite;
Then you can access it:
http://arsdnet.net/cgi-bin/apidemo2/obj/cool/
BTW the trailing slash is mandatory: this is one of the outstanding bugs I haven't gotten around to fixing yet. (The trailing slash code is more complicated than it should be, making this harder to fix that it might look.)
Anyway, you can see the object rendered itself as html via makeHtmlElement. This is a good time to showcase other formats:
http://arsdnet.net/cgi-bin/apidemo2/obj/cool/?format=table
table, also try csv, and of course, json
http://arsdnet.net/cgi-bin/apidemo2/obj/cool/?format=json
or for machine consumption:
http://arsdnet.net/cgi-bin/apidemo2/obj/cool/?format=json&envelopeFormat=json
and the property is available too:
http://arsdnet.net/cgi-bin/apidemo2/obj/cool/id
Another major outstanding bug is that the automatically generated Javascript functions can't access child objects at all. They only work on functions on the top level ApiProvider. Another bug that is harder to fix than it might seem, and I'm not particularly driven to do so because the top-level functions can do it all anyway. Of course, you could make the URLs yourself on the xmlhttprequest and access it that way.
Let's also demo POST by slapping together a quick form:
http://arsdnet.net/cgi-bin/apidemo2/poster
you can submit something and see the POST handler indeed reset the name. (BTW note the action has that trailing slash: without it, it silently redirects you! I really should fix that.)
Anyway, bugs notwithstanding, the core of it works and might be the closest thing to full blown REST D has right now.
At the moment of writing this text there is no framework for building true RESTful web services that I know of. However, you should be able to easily build one on top of vibe.d or Adam's web modules that he already mentioned above.
You can take a look at what I'm building. Still extremely alpha, but I'm attempting to build a Rails-like framework in D: http://jaredonline.github.io/action-pack/
I know this is a really late answer, but I figured someone might come by this one day, since it has been so long and a lot of changes has happened within the D community, especially towards web development.
With Diamond you can write RESTful web applications without hacking something together, since it supports it within the framework.
http://diamondmvc.org/docs/backend/#rest
You can try Hunt Framework.
routes setting
GET /user/{id} user.detail
app/UserController.d souce code:
module app.controller.UserController;
import hunt.framework;
class User
{
int id;
string name;
}
class UserController : Controller
{
mixin MakeController;
#Action
JsonResponse detail(int id)
{
auto user = new User;
user.id = id;
user.name = "test";
return new JsonResponse(user);
}
}
Request http://localhost:8080/user/123
{
"id": 123,
"name": "test"
}
I am using Tastypie, Django for my project.
To Update a many to many field I have used save_m2m hook.
def save_m2m(self, bundle):
for field_name, field_object in self.fields.items():
if not getattr(field_object, 'is_m2m', False):
continue
if not field_object.attribute:
continue
if field_object.readonly:
continue
related_mngr = getattr(bundle.obj, field_object.attribute)
related_objs = []
print bundle.data[field_name]
for related_bundle in bundle.data[field_name]:
try:
stock = Stock.objects.get(nse_symbol = related_bundle.obj.nse_symbol)
print stock.__dict__
except Stock.DoesNotExist as e:
dataa = {"error_message": e}
raise ImmediateHttpResponse(response=HttpBadRequest(content=json.dumps(dataa), content_type="application/json; charset=UTF-8"))
related_objs.append(stock)
related_mngr.add(*related_objs)
Now I want to remove elements from the same many to many field.
How should I achieve this. Do I have to send a patch request or delete request and how to handle this.
I am begineer in tastypie. I googled it some time and I couldn't find a proper way. Please guide me how to complete this.
Thanks.
I've thought a lot about handing m2m relationships, since most of our app depends on m2m links.
I've settled for the approach of an update method. Pass in the all the references of the relationships you want changed (add and remove), then update the db accordingly. We only pass in the changed values, since if you have a paginated list, you only want to update the items the user has identified. Generally I use a custom hook for this defined in override_urls.
I used to have a separate add and remove method, which worked well until we changed the gui and allowed users simply to change checkboxes. In that approach having an update method was much more useful. You'll have to decide on which method suits your application the best.
I am writing a small sample program and I would like to override the default pyglet's behavioyr of ESC closing the app. I have something to the extent of:
window = pyglet.window.Window()
#window.event
def on_key_press(symbol, modifiers):
if symbol == pyglet.window.key.ESCAPE:
pass
but that does not seem to work.
I know the question is old, but just in case. You've got to return pyglet.event.EVENT_HANDLED to prevent default behaviour. I didn't test it, but in theory this should work:
#window.event
def on_key_press(symbol, modifiers):
if symbol == pyglet.window.key.ESCAPE:
return pyglet.event.EVENT_HANDLED
Same for me. The question is old, but I've found out that you should use window handlers mechanisms, thus making the current event not to propagate further.
You can prevent the remaining event
handlers in the stack from receiving
the event by returning a true value.
The following event handler, when
pushed onto the window, will prevent
the escape key from exiting the
program:
def on_key_press(symbol, modifiers):
if symbol == key.ESCAPE:
return True
window.push_handlers(on_key_press)
Here is that link
On the Google group for pyglet-users it is suggest could overload the window.Window.on_key_press(), although there are no code example of it.
It's simple actually, subclass Window and overide the on_key_press, like this:
class MyWindow(pyglet.window.Window):
def on_key_press(self, symbol, modifiers):
if symbol == key.ESCAPE:
return pyglet.event.EVENT_HANDLED