By anner on
I just finished implementing a little php interface to a mysql db, easy enough to do...took an hour or so. My question is what is the benefit to using the drupal forms API over writing your own php forms? I coded this myself, and it was quick enough. Saved me from having to learn a new interface, so I think it was actually faster. Thoughts?
Comments
sorry, but what is php forms
sorry, but what is php forms ?
----------------
Regards,
Dmitry Kresin, ARDAS group - Web site development, Drupal services, Software development, IT outsourcing.
Reasons for using the Drupal forms API
Some things I see as an advantage of using the Drupal API forms (in no particular order); Once you learn it, you can roll out forms quickly, it provides the logic for validation and redisplaying to form if errors, it provides a clean way for seperating out both validation and submition from form generation, it provides extensions beyond standard forms (autocomplete for example) and allows others to provide extenstions, it seperates defining the form from the generation of the html and makes it straightforward to theme the output different if you choose, it allows others to extend/add elements to existing forms. In short, it provides a nice tool kit for building forms.
But all that aside if you want to make a module that defines a content type based on a node (which has advantages of its own) you need to know the forms API. If you want to define a module with a custom block that has configuration options you need to know the forms API. And if you want to define a module that uses the standard settings interface you need to know the forms API.
i tried using forms api but cant seem to know how it works
hi nevets,
I wanted your help as I read your post regarding the plus points of using forms api. I had done the following
created an html form with a textfield username and a submit button.
My requirement was that upon submission these passed params should be displayed on a page. But how do i go about doing that.
Initially I wrote a simple php code which just displays the elements that it gets from the GET array and upon creation this page was given node no node/14
I put in action for the form I created as node/14. But as obvious as it was when user enters name and clicks on submit these params are passed to a static page. During that time I hunted the drupal site for a form api and came across the api described at http://drupal.org/node/37775 and also went through the quick start guide. But as in the quick start guide they gave code for form creation as
Where does this code go? in create content -> page. I did not understand this part.
I'd greatly appreciate any help form your side
Small form sample
Here is a small sample, make a file in modules/myform called myform.module and paste the following code into it.
Enable the module to see it in action
thanks for the example, Nevets!
Nevets:
I'd like to thank you very much for providing an example! This is 100 times more helpful than posting all the API functions. Drupal really should have added something like this to the "Forms API Quickstart Guide".
There is a forms api quickstart guide
If I remember correctly it can be found at http://api.drupal.org
-Olegu
http://www.zbz5.net/
Thanks!
Very helpful example.
Ditto
Yeah, again, this example was wayyy better than anything on the api reference site or in the handbooks. The API reference site should include something like this under its examples.
Modifying the edit form. An example, anyone?
We would like to reorganize and simplify the editing form for both Page and Story module.
But this Form API and the form tree seem so complicated, and so fragmented across multiple hooks, that it's just impossible for a non-drupal guru to get a handle on any of it without a huge amount of study and a level of documentation that doesn't seem to exist yet.
Can someone please give me a clue about how to approach this problem:
Presently, the "Tags" textbox is displayed in a with the reading "categories". We want to add a second tags field just like it (for particular kinds of tags) , and then wrap both fieldsets in a larger container Div (or other fieldset) which can converted to tab container with client side javascript (bypassing the existing collapser.js). Thus, both fieldsets will be converted to Tabs within the tabs container. This part is easy, IF I can maniulate the form source with classes and HTML elements that make sense to my tabs code.
The Form_Alter hook lets me act on the form tree via a formID, but I don't understand how to reorganize chunks of the form tree here, or whether I even can do that at all.
(It doesn't seem this is what form_alter is really for, being geared more to minor tweaks than to big structural changes to the tree).
The only real discussion I have find of manipulating the tree at all is this linl, and it is so dense and writtren for experts, that no mere mortals can make heads or tails of it. Further, other users report the code example doesn't work at all.
http://drupal.org/node/48643
Is there any example anywhere of someone redesigning the way the user's settings and data entry forms can be organized? If we could see one example of how things were hooked and configured for say, the Page module, it shouldn't be too hard to extrapolate from there.
Just one example...please.. just one? Drupal's node editing is hardly compact, or even very intuitive. We cannot believe we are the first to want to spruce it up a bit, nor can we believe it's quite as hard as it seems to be.
Maybe this will help
Basically what you want to do is move the form element from the existing form to a spot "lower" in the tree. In the example that follows for the page module edit form, we wrap the taxonomy fieldset in our own fieldset (not very pratical, but hopeful it will help you progress).
Word of warning, your module must either be alphabitically after the module whos fields you want to modify or have a greater weight.
To try it out make a directory called zformmodifier under the modules directory and place the example below in a file called zformmodifier.module.
');
// Get the part of the form we want to wrap
$taxonomy = $form['taxonomy'];
// Remove it from the form
unset($form['taxonomy']);
// Add the wrapper, here we just use a fieldset
$form['taxonomywrapper'] = array('#type' => 'fieldset',
'#title' => 'My taxonomy wrapper',
'#weight' => $taxonomy['#weight']);
// Now add the original form part back as a child of the wrapper
$form['taxonomywrapper']['taxonomy'] = $taxonomy;
}
}
I agree with the plea
Yes, if you know how to do forms in HTML with PHP already, and you want a normal enter-submit form where you catch all your content yourself, the API does seem to just get in the way
But once you want to work with validation, persistance and themes, it starts paying off.
And when (like this query) you want to modify an existing Drupal form, it's gold.
(But still a bit painful)
My methods are -
That's what the demo_install does. I listed it above because you have to have it there from the very start of testing or it gets hairy.
I believe your desire for 'tabs' (A major restructuring, I think) could begin to be addressed by trying to go :
... works for me, take it from there!
.dan.
How to troubleshoot Drupal | http://www.coders.co.nz/
.dan. is the New Zealand Drupal Developer working on Government Web Standards
Thanks to both of you
Nevets, Dman..
Thank you both for the extensive replies. I will now delve into your solution and let you know how I progressed.
I think dman is reading my frustration about this whole API business well. I consider myself a developer, but not a programmer with a deep skillset. Someone like me has little trouble with most CMS systems using templates, or some other view system, but drupal just jams my mental circuits completely. Even so, I suspect I have many more skills than most users who just want to add some degree of customization to the standard content admin forms--and have more time to try and wrestle with it.
Perhaps some of those confused users can add a comment here, and suggest just how significant the problem is--and for how many. I suspect this is one of those very large issues that just doesn't get mentioned enough because people fear they are just missing something and will look stupid asking for help.
The Drupal community boasts about how powerful and flexible the system is, but if making basic changes to the way users interface a node's attributes and permissions is this complex, it's hard to really sustain that boast to any but the most skilled or persistent developers with a lot of time to invest.
Perhaps there is some middle ground wizard helper that could provide a more traditional templating mechanism that treats the form/tree elements as simple template variables of some sort? That way, the designer (me, could just layout the named elements in a visual way, and let drupal and the engineers worry about the innards.
We're really pretty happy with what we've been able to do thus far. Drupal made some of the expected difficult tasks easy. It's the things we assumed would be easy that are proving very hard.
Oh well, back to it. Thanks again for the detailed help.
Developing is for developers
What you are asking is beyond almost every templating system out there.
Take a working, inline portion of a dynamically rendered, themed part of core UI, place it elsewhere in the page and still work. Yo'd have to do it with string parsing!
And remember that themes kick in all over the place, so you should never be coding ANY HTML.
At no time could there be a 'template' listing, say :
for you to mess with, as
- what shows up when is programatic,
- the ordering of the fields is programatic,
- and it's 'altered' by other modules inserting their own blocks at any time.
Instead, we have
... which isn't that different conceptually.
You have direct access to the variable values at all times.
You can change the order or nesting as needed today.
You can even set the titles or descriptions of fields from other modules.
Prior to forms API, custom modules only had access to the concatenated STRING version of the rendered form parts.
Note also, at the far end of this process, it would have been possible to get similar results just through theming - you impliment your own theme_form() and render just the form elements you want, in the order you want. That's where you go if you are keener to work with HTML than code.
It depends on if you see this enhancement a structural or visual change. I gave you the semantic solution. The layout-driven solution comes from the other end.
... that's pseudo-template code (Meaning it probably won't work as-is), and possibly contains a gotcha or two, but it does the same thing at RENDER time rather than code time.
.dan.
How to troubleshoot Drupal | http://www.coders.co.nz/
.dan. is the New Zealand Drupal Developer working on Government Web Standards
Theme forms with form_id
I'd recommend to theme specific forms by their form_id or callback: theme_form_id or theme_callback.
--
The Manual | Troubleshooting FAQ | Tips for posting | Make Backups! | Consider creating a Test site.
Good point
I knew I was overlooking/forgetting one big step :-B Makes more sense, I felt something was a bit screwy with the implimentation, but I knew the theory I was aiming at.
Just an untested brain-fart.
.dan.
How to troubleshoot Drupal | http://www.coders.co.nz/
.dan. is the New Zealand Drupal Developer working on Government Web Standards
The reason
in traditional HTML layout, a form is dirt simple. There's nothing -- technically, at least -- that prevents you from sticking HTML form data right in your node's body. You can point the form to a url on your drupal site, and write a module that takes the incoming $_POST[] data and processes it.
FormAPI exists not because making HTML forms is so hard, but because a robust API is needed to define forms in a modular fashion so that other plugin modules and other themes can rearrange, dynamically alter, make additions to, and override the default behavior of any other forms in the system.
As a result, changing the layout and behaviour of core drupal forms may require some code, but it can be done without changing *any of the core files* in the drupal system. That makes upgrading and security easier, and also helps you keep better track of the changes you're making versus what was there already.
You might look at the webform.module if all you want to do is make a simple form that takes data and emails it, or something like that. It, too, uses FormAPI as its backend -- it just presents a friendly front-end for those who don't need the complexities.
--
Eaton's blog | VotingAPI discussion
--
Eaton — Partner at Autogram
You can point the form to a
Im not sure about that. I have made a simple block with a php self form and it works only to Admin and non registered users. No way to make it work with registered users.
I dont want to learn an API, i only want to use my old php code on drupal...
Any help?
I have asked this on the forum with no luck here:
http://drupal.org/node/186782
Thank you very much
Eaton is right. FAPI helps
Eaton is right.
FAPI helps to hide complexity and provide nice features for site developers. For instance, there is no resizable textarea in HTML (you need to write javascript for that). FAPI gives you a simple way to specify resizable => TRUE and that's all. You can develop your own complex form elements and easily use them on your form such as tabs from jstools.module.
I can compare Drupal FAPI form development with something like Visual C++ IDE where you can just choose a desired element and drop it onto the form and then fill its attributes :)
----------------
Regards,
Dmitry Kresin, ARDAS group - Web site development, Drupal services, Software development, IT outsourcing.
Thanks for the great example...
Could you comment on what function to call from a node template?
From your example, I would want to do this:
However, when I add this to my node template, I get an "internal server error".
:(
Am I even on the right track?
Not sure what you are trying to achieve
but for the example you need to create the module myform (the example goes in a file called myform.module in the directory modules/myform). Note if you are using Drupal 5 you will also need a myform.info file (see below). Copy the sample and place in myform.module, then enable the module. Now you can use the path 'myform/sample' to access the form. If you site is at http://www.example.com the URL would be http://www.example.com/myform/sample (without clean URLS that would be http://www.example.com/index.php?q=myform/sample).
If using Drupal 5 you will also need a myform.info (also in modules/myform) that looks something like this
Thanks.
Thanks for the response.
I see how you got to your explanation.
Primarily, I see this:
This is where you declare from where the form will be accessible.
I am using the contemplate module. I have a content type of item (custom one). Beyond this I am using the contemplate module to make the custom node type appear the way I want to in terms of layout. Nothing fancy really, just an HTML template that has all the right variables in the locations I want them to show up in the HTML template's layout.
What I am looking to do is make this form be part of this template. I am not using your exact form example, but I made two hidden elements and kept the submit button. I also am using your validate and submit functions.
So in my module I have the form building, the validate function, and the submit function.
In fact, here is my module code:
My question is what am I missing from the proper usage and how would I go about having this form be part of every custom node content?
If I understand correctly you are trying to add a "buy" button
If I understand you are trying to add a "buy" button to certain content types. There are at least a couple of ways you could approach this, the easy one would be to the link hook to add a "buy" link to the approriate content types, you can also also only add the link for people who are logged in or might make it "login to buy" for people who are not logged in.
You could also use the nodeapi hook to add the form to during the 'view' op when viewing the selected content. Note you can once again choose to show/not show the button based on if someone is logged in or not (or vary the text of the button)
Side notes, no real need to add $user->uid or $node->nid. $user->uid will be the same when view the form and on validate (using global $user) and if the form is for a node, $form_values already has the nid. It is also better to use '#type' => 'value' (than hidden) as it truely hides the values (the user can not even see them if they look at the html).
Coolness
That's exactly what I am trying to do.
I think I follow your points, let me see:
I am using the nodeapi's view operation to enact other things in my node. I can drop all of that code into my view operation.
Then, I also change all instances of
'#type' => 'hidden'to'#type' => 'value'.This is also brought up in the API QuickStart Guide:
"If a form has a submit function, then hidden form values are not needed."
I'm still not clear on this point you made:
"Side notes, no real need to add $user->uid or $node->nid. $user->uid will be the same when view the form and on validate (using global $user) and if the form is for a node, $form_values already has the nid."
Finally, if I put all this code into my nodeapi's view operation (already did this), what code do I insert into my HTML template so the button this form has within it gets displayed?
I think once I understand these two things I will be in really good shape.
nodeapi view op
What code would you use to make this work in the nodeapi hook under the view op?
Could you fill this in as an example?
What code would I use in my node template to get it to display in a particular table cell?
Could you fill this in as an example?
The format of $node->content is the same as used by Forms API.
Positive weight should put your addition below the normal body, negative above it
... I imagine. Never actually tried it myself
.dan.
How to troubleshoot Drupal | http://www.coders.co.nz/
.dan. is the New Zealand Drupal Developer working on Government Web Standards
I got an error when I tried to use the example
Hi Nevets, When I tried to use the example, I got the following error:
Any idea what I am doing wrong?
Same here, Drupal upgrades
Same here, Drupal upgrades must have broken this...?
Is there a solution?
here's my error:
warning: call_user_func_array() [function.call-user-func-array]: First argument is expected to be a valid callback, 'myform_sample' was given in /var/www/drupal-5.3/includes/form.inc on line 217.Solution
I was having the same problem, when I looked in the API and realized in 5.2 there's only 1 argument in drupal_get_form(); I also looked in the handbook at this tutorial (http://drupal.org/node/82936) and instead, now do return system_settings_form($form); at the end of your myform_sampleform().
hth,
Paul
---------------------------------------------------------------
My drupal site: Vacation-Places
I get an error
Hi
I am trying to follow your example to learn about form API.
I get the following error :
Did I do something wrong?
Regards.
Michel.
Hi, I want to display Create
Hi,
I want to display Create content poll form in block.
I found your link while i am trying to produce form for Create content poll and I think you can help me.
I write form codes manually but I stuck with data validation error for form_token. I write php code for it which i found in forum and same error again . The codes are here :-
I also try to call drupal form function in block but fail :-
I still struggle for success. Please help me.
Visit me at http://nashikit.com
Correct token
print drupal_get_token('poll-form');You need to use the right value, which would be (from the top of my head): poll_node_form. However, I'm sure this approach is doomed.
As to II: how does it fail? Do you use the core poll module or another module?
Node forms can be printed elsewhere with:
PS It's best to open a new thread for these kind of questions.
--
The Manual | Troubleshooting FAQ | Tips for posting | How to report a security issue.
Thanks for reply.
Hi,
I change in codes as per your suggestion
but still I get the warning message
"Validation error, please try again. If this error persists, please contact the site administrator."Any idea?
The URL of the site :- http://tveed.com/?q=frontpage
Thanks again for your helping hand.
Visit me at http://nashikit.com
Success
Hi,
Thanks Heine,
I get success with the codes
Visit me at http://nashikit.com
To embed an existing form
To embed an existing form into another form or any other place try to use www.drupal.org/project/subform_element
This module allows you to build a form which consists of one subform element which embeds any of existing forms.
----------------
Regards,
Dmitry Kresin, ARDAS group - Web site development, Drupal services, Software development, IT outsourcing.
retrieving form_state from custom form
hi did u solve your problem?
i am trying to create this form and retrieve the values of the checkboxes to be processed in drupal. perhaps you can help me get started. the rest of my post is here http://drupal.org/node/777464
hi All
I am trying to get the values from a form a created in drupal 6.x. i have not used this type of code to create the form
because it is too cumbersome to create the form i wanted. instead i have used code like this
as u can see im trying to get the values out of my custom HTML form but i am unable to do so...
please could somebody help me...
thanks
chris
Well, that was a mistake
Well, that was a mistake then.
Don't do it that way.
Either use the Form API, or do your own form handling, but you can't make it up as you go along and get the advantage of built-in Form validation and processing at the same time.
Only after you've totally understood Form API successfully would you know what rules to break and override as you are trying to do here.
For now, just build your forms by hand - if Form API isn't making sense to you yet.
.dan. is the New Zealand Drupal Developer working on Government Web Standards
Form API of Drupal 4.7 is the best for developers...
Remember that Form API, is an API. Once you know how to work with it, you will see how you save your time. A lot of functionality is yet implemented and you don't need to worry about that, form validation, form submition handler, form custom theming, and many other.
If you take one day to learn how to use it, you will save a lot of time and bugs.
Ronny
Ok, I see your points, and
Ok, I see your points, and will learn it if I need to make or edit a module. But if I have one or two simple forms, a day may be more of an investment than my employer would appreciate. Another point: would form API code be portable? If I was forced by my employer to move everything out of drupal (either into another cms or into static content) the form API stuff would all have to be recoded in pure php/html, right? Since they (the ptb) haven't signed off on drupal officially yet, I think I'll hold off on the form API stuff for now.
A word of advance
If you are going to place html/php forms in a node and the form has any side effects (place something in a database, email, etc) I would strongly recommend using the excerpt module and hand setting the excerpt/teaser. Otherwise you can find the code running twice (once for teaser, once for full view with unwanted results).
I already use this. Thanks
I already use this. Thanks
Ok, if that is the point, I
Ok, if that is the point, I agree with you, but if ou are developing Drupal Modules I strongly recommend that you take a time to learn how good is it.
As a former mambo user/coder...
I have to say that drupal's form api makes module development so much quicker. It does take getting used to, but it is a functional api. In fact, the whole module API system is like a godsend from the direct coding I had to do to get mambo modules working.
www.thelinuxuser.com
There is another (hidden) problem with using the API...
OK, so I have decided to go the API route and though struggling along, I am making progress.
The API is an impressive work, feature rich and capable. Well done! I will never know whether the hours and hours I invested in the API would not have been better served (and more profitable) through building more websites rather than coding and learning the API. But now I have wonderful, capable, state-of-the-art websites.
I have another problem with the API though. And that is that from one Drupal version to the next Drupal upgrade the API changes. And sometimes the API undergoes considerable changes. That means that I have to go from one already written and running website to the next exsiting website and modify themes, modules and custom code in order to upgrade. I hate fiddling with things that already works and has been running for a while! Sometimes progress sux! And the more custom code that uses the API, the bigger this workload becomes. It feels like two steps forward and one step backwards every time an upgrade comes along!
And (see the 4.7.4 upgrade) sometimes code tweaking is necessary not even with major upgrades but with security fixes as well.
As Drupal sites grow, in terms of size, features and complexity, I can visualise a substantial liability in adapting existing code in future! It is a bit like having the Y2K-coding crisis every six months!
I doubt that it is workable for a code-compatibility upgrade path to exist in Drupal where I did not have to tweak code that already works, but it would have been nice...
Casper Labuschagne
Where am I on the Drupal map on Frapper?
Honestly speaking, Drupal
Honestly speaking, Drupal Form API is one of the greatest features in Drupal which makes it to be much better than any other CMS :)
----------------
Regards,
Dmitry Kresin, ARDAS group - Web site development, Drupal services, Software development, IT outsourcing.
Subscribing -- Sharique
Subscribing
--
Sharique uddin Ahmed Farooqui
Web Developer
http://it.Managefolio.com
Sharique Ahmed Farooqui
Subscribing I also have a
Subscribing
I also have a First argument is expected to be a valid callback, '_node_form' was given in form.inc on line 217 but nodecomment module with cck , greetings, Martijn
Hi, im trying to put the
Hi, im trying to put the example to work, but i get the same error:
With all the corrections, im lost now and dont know what to do. Can someone update the example with all features inclused? Im working on drupal 5.x.
If anyone can also help me in this:
My module is based on print an output, like:
And i need an autocomplete feature for my input (from a custom table). im trying to make the example work, to later use the autocomplete feature like:
http://drupal.org/node/42552
How to make my input work with autocomplete? I need serious and newby-oriented help with forms, and the documentation is a lil complex for me... where to find newby-oriented help, with examples and all? :'(
txs
pd] hopefully, i need help newbie-oriented for drupal... :'(
Small Form Sample - Drupal 6.x update
OK, finally got a version of nevets Small Form Sample to work in Drupal 6.x.
Create myform.info, myform.mofule and save to /sites/all/modules/myform
Go to /admin/build/modules, enable 'Small Form Sample' and Save configuation
Go to /admin/user/permissions, enable 'myForm module' and Save permissions
Go to /myform/sample and test.
I'm a bit of a Drupal newbie and I'm not sure if everything I changed was needed but it works for me.
Can anyone can see a problem or a better way?
Thanks steve it worked!!!!
Thanks steve it worked for me - I agree with everybody else - there is nothing that shows how to implement custom forms correctly.
Now its play time!!!!!
Small Form Sample - With no redirect (6.x)
I wanted to stay on the same page with no redirects and have all the form data available for the function that creates the page. I can then show the form and handle the form results on the same page. The only hack required is one global variable in the module but no changes to the core.
First I adjusted to the menu to call a function in the module for display not call the form API directly. This function, myform_display_page(), calls the form api to build and check the form.
I looked over the form API and didn't see a way to avoid using a global but its limited to one variable I prefixed with the module name to avoid any naming conflicts.
This variable is set in the myform_sample_submit() function that is called when the form is correctly filled out. By testing to see if the variable has been set we can tell if the form passed validation.
Be sure to go to the module list if your updating the previous example. Then give yourself permission to use the module as the name of the permission needed has changed. Browse to /myform to see the form in action.
If anyone has a way around the use of the global, I'd love to hear about it. I'm rather new to Drupal so I've a lot of reading to do to catch up.
$form_state['rebuild'] = TRUE
It sounds like what you want is to set $form_state['rebuild'] = TRUE in your submit handler. That will cause the form to be rebuilt. Your form building function will get a copy of the populated form_state, and there will be no redirection. That'll give you a chance to add additional information in the form building function itself.
--
Lullabot! | Eaton's blog | VotingAPI discussion
--
Eaton — Partner at Autogram
what about $form_state
I'm not sure how to get access to $form_state after the redirect. $form_state contains the form values and some other variables (more reading lol)
If I prevent the redirect and save a copy of $form_state I at least have access to all the data without using the form data to create the url on redirect as used in a previous example.
for buildign function
The function that actually constructs the form itself -- say, function mymodule_admin_form() {...} or something like that -- gets a copy of the form_state as its first parameter...
--
Lullabot! | Eaton's blog | VotingAPI discussion
--
Eaton — Partner at Autogram
If you set '#required' =>
If you set
'#required' => TRUE
for the form element you don't need those validation options testing for empty fields
My Drupal sites:
Reworked no-redirect based upon other users suggestion
This is my first step to making my own modules by learning about forms. I have to say I am impressed by the Drupal codebase. I am really impressed by the form functions. Very beautiful design. This is going to work nicely for my site. My favorite is the way it looks when a field is missing and is required. Very professional looking.
Page not found - Error
I'm a Drupal newbie. Using 6.13. I created and installed myform.info, myform.module and enabled it but I get an error "Page not found" when I go to /myform/sample
look at /myform instead - if
look at /myform instead - if you look at the navigation menu you'll see it adds a menu item for you.
http://modelagnostic.co.uk/
sub
sub
where are my form_state values
Edit by nevets
Folks please do not double post issues and please do not hijack other threads with new issues.
This was a dup of: http://drupal.org/node/409344
Scott Baetz
Web Developer
sbaetz@admininternet.net
AdminInternet
http://www.admininternet.net