You are not logged in.
I'm building a custom module (my own code in /custom/admin/modules/module-name/) and trying to follow BigTree's existing code base as much as possible, and am trying to figure out how to handle a image / file upload through the module.
Of course I can do an <input type="file" /> and move_uploaded_file(), but I want to stay within the realm of BigTree to maintain compatibility, take advantage of the cloud storage integrations, etc.
I see some stuff in /core/admin/form-field-types/(draw/process)/upload.php, but I don't think they're meant to be accessed directly.
How should I go about this to leverage the cool and useful code BigTree already has? Thanks!
Offline
You can approach it a few different ways. If you want to handle everything yourself except for storage, you can use the BigTreeStorage class to move the file into place like this:
$storage = new BigTreeStorage;
$file_path = $storage->store($_FILES["uploaded_file"]["tmp_name"],$_FILES["uploaded_file"]["name"],"directory/to/store/to/");
That will handle things like determining the safety of the file (no executables or scripts), the file name (turns spaces into dashes, makes all lowercase, strips special chars), and where it should be stored (if Cloud Storage is enabled it will store there). The last parameter in the store method is the "relative" directory to /site/ or the cloud storage bucket's root folder.
If you want BigTree to do even more, you can replicate the behavior of a form field and use BigTreeAdmin's processField method. This provides things like error handling for you.
$field = array(
"type" => "upload",
"title" => "My Upload Field",
"key" => "uploaded_file",
"options" => array("directory" => "directory/to/store/to/"),
"file_input" => $_FILES["uploaded_file"]
);
$file_path = BigTreeAdmin::processField($field);
In this example, $file_path will either contain the full path of the stored file or null if the upload failed. If the upload fails, $bigtree["errors"] will contain error messages pertaining to why it failed.
The processField approach is even more valuable if you're doing image processing. You can adjust the "options" array to do things like automatically create thumbnails and center crops. It also supports setting up crop information, but you need to then replicate the cropping process which is a bit more complicated. An example options array for thumbnails and center crops:
array(
"image" => true,
"thumbs" => array(
array("prefix" => "small_","width" => "300","height" => "300")
),
"center_crops" => array(
array("prefix" => "crop_","width" => "500","height" => "500")
)
)
Offline
Awesome, I'll give this a try. Thanks Tim!
Offline
In the case of "drawing" the field, is that something I could piggy-back on too? I have the code:
$field = array(
'title' => '', // The title given by the developer to draw as the label (drawn automatically)
'subtitle' => '', // The subtitle given by the developer to draw as the smaller part of the label (drawn automatically)
'key' => 'image', // The value you should use for the "name" attribute of your form field
'value' => '', // The existing value for this form field
'id' => 'category_image', // A unique ID you can assign to your form field for use in JavaScript
'tabindex' => '', // The current tab index you can use for the "tabindex" attribute of your form field
'options' => array(
'image' => true
),
'required' => false // A boolean value of whether this form field is required or not
);
include(BigTree::path('admin/form-field-types/draw/upload.php'));
Is there a shortcut function to do something similar, or is this the best practice?
Also, it displays the options of both Upload or Browse. When I click the Upload button it allows me to browse my computer like a normal file upload, but when I click the Browse button nothing happens. I'm guessing there has to be some supplemental JS to go along with it (and maybe the shortcut function includes it, or if not, what do I need to include for that)?
Sorry for all the questions, just trying to make sure we develop this module the best way possible. Thanks!
Last edited by mdewyer (April 8, 2015 12:52pm)
Offline
Solved it. The selector for the Javascript to handle the media browsing, on file input change, etc. is:
.container form
So make sure your form is inside a element with the class of "container"!
Offline