Upload and use custom JavaScript file in SilverStripe - silverstripe

My project has a crossword. The client would like to upload JavaScript files and change the pattern.
How do I make the upload file and include the JavaScript in the front end of the website? The file is getting uploaded but it is not showing up in source code.

The following is for SilverStripe 3.1.
This example adds a JavaScript file upload to each page. In the Controller's init() function if a file has been uploaded we load it into the page:
Page.php
class Page extends SiteTree {
private static $has_one = array(
'CustomJavascriptFile' => 'File'
);
public function getCMSFields()
{
$fields = parent::getCMSFields();
$customJavascriptFile = UploadField::create('CustomJavascriptFile', 'Custom Javascript File');
$customJavascriptFile->setFolderName('javascript');
$customJavascriptFile->setAllowedExtensions(array('js'));
$fields->addFieldToTab('Root.Javascript', $customJavascriptFile);
return $fields;
}
}
class Page_Controller extends ContentController {
public function init() {
parent::init();
if ($this->CustomJavascriptFileID) {
Requirements::javascript($this->CustomJavascriptFile()->RelativeLink());
}
}
}
This method gives us a custom JavaScript file per page. We could alternatively have the file uploaded to the Config Settings instead so we can upload one file that is then loaded for the whole site.
First we need to extend SiteConfig. We need to declare the extension in our config.yml:
mysite/_config/config.yml
---
Name: site
After: 'framework/*','cms/*'
---
SiteConfig:
extensions:
- CustomSiteConfig
CustomSiteConfig.php
class CustomSiteConfig extends DataExtension {
private static $has_one = array(
'CustomJavascriptFile' => 'File'
);
public function updateCMSFields(FieldList $fields) {
$customJavascriptFile = UploadField::create('CustomJavascriptFile', 'Custom Javascript File');
$customJavascriptFile->setFolderName('javascript');
$customJavascriptFile->setAllowedExtensions(array('js'));
$fields->addFieldToTab('Root.Javascript', $customJavascriptFile);
}
}
Page.php
class Page extends SiteTree {
}
class Page_Controller extends ContentController {
public function init() {
parent::init();
$siteConfig = SiteConfig::current_site_config();
if ($siteConfig->CustomJavascriptFileID) {
Requirements::javascript($siteConfig->CustomJavascriptFile()->RelativeLink());
}
}
}

Related

Remove default HtmlEditorField from Page

Is there a way to remove/disable the default HtmlEditorField (Content) from a Page in back-end from SilverStripe 4.2.2?
From your Page or subclass of Page:
public function getCMSFields()
{
$fields = parent::getCMSFields();
$fields->removeByName('Root.Main.Content');
return $fields;
}
Or as an extension:
class RemoveContentExtension extends \SilverStripe\ORM\DataExtension
{
public function updateCMSFields(\SilverStripe\Forms\FieldList $fields)
{
$fields->removeByName('Root.Main.Content');
}
}
And apply the extension to your page with YAML config:
# File: app/_config/content.yml
MyPage:
extensions:
- RemoveContentExtension

How do I register widget assets in Yii2?

I want to create a custom widget in yii2 with its css and js files. Inside 'components' folder I've created a 'myWidget' folder and inside of it:
- myWidget.php which extends yii\base\Widget.
- myWidgetAsset.php which extends yii\web\AssetBundle.
- views folder containing index.php file.
- assets folder containing main.css and main.js files.
Here are the codes: myWidget.php
namespace app\components\myWidget;
use app\components\tablaFoS\tablaFoSAsset;
use app\models\DisciplinesGrandesAreas;
use yii\base\Widget;
class myWidget extends Widget {
public function run() {
parent::run();
return $this->render('index');
}
}
myWidgetAsset.php
namespace app\components\myWidget;
use yii\web\AssetBundle;
class myWidgetAsset extends AssetBundle {
public $basePath = '#webroot';
public $baseUrl = '#web';
public $css = ['assets/main.css'];
public $js = ['assets/main.js'];
public $depends = [
];
}
When I see the generated code I got:
<link rel="stylesheet" href="/assets/main.css"></link>
<script src="/assets/main.js"></script>
instead of something like e.g.bootstrap:
<link href="/becyt/assets/67099f30/css/bootstrap.css" rel="stylesheet">
What am I doing wrong? What am I missing? Thanks in advance.
You could register your AssetBundle in the widget's init() function like this:
public function init() {
MyAssetBundle::register( $this->getView() );
parent::init();
}
To publish your asset files, you should set sourcePath instead of basePath and baseUrl, e.g. :
class myWidgetAsset extends AssetBundle {
public $sourcePath = '#app/components/myWidget/assets';
public $css = ['main.css'];
public $js = ['main.js'];
}
Read more in official guide here :
source assets: the asset files are located together with PHP source
code which cannot be directly accessed via Web. In order to use source
assets in a page, they should be copied to a Web directory and turned
into the so-called published assets.
And of course don't forget to register this asset bundle in your widget run() method.
You can also register a widgets assets like
<?php
use yii\helpers\Html;
use yii\helpers\Url;
use yii\widgets\ActiveForm;
\marqu3s\summernote\SummernoteAsset::register($this);

Setting up a framework-only SilverStripe site

I'm looking to create a framework only SilverStripe website, however I have been unable to correctly set up the routing for it.
I want to have a single controller handling a handful of URLs. I want it to handle an empty URL too, i.e. '/'.
I've been unable to get my controller to differentiate between the different urls.
My routes are as follows:
---
Name: rootroutes
---
Director:
rules:
'$Action/$ID/$OtherID': 'MainController'
'': 'MainController'
and my controller:
class MainController extends Controller {
private static $url_handlers = array(
'$Action//$ID/$OtherID' => 'handleAction',
);
public function index() {
return "index";
}
public function login() {
return "login";
}
public function handleAction($request, $action) {
var_dump($action); // always 'index'
if($this->hasMethod($action)) {
return $this->$action();
}
}
}
You need to define the $allowed_actions array on your controller before actions other than index() will work.

Silverstripe 3 - extend sitetree and layout

I'm a newbie in SilverStripe. I need to create a new page by extending a new class sitetree. My question is how to retrieve in the template something like $Layou which is used in the classic page.php. For example, in my template folder I would like to have a folder like "Layout" organized for new pages created from this.
this is the controller:
class WhitePage extends SiteTree {
private static $db = array(
);
private static $has_one = array(
);
}
class WhitePage_Controller extends ContentController {
private static $allowed_actions = array(
);
public function init() {
parent::init();
}
function index() {
return $this->renderWith("WhitePage");
}
}
i would like in the template directory create a folder name "whitepage" within the ".ss" file, and in the template use something like $whitepage instate of $Layout ...
How to do this?
thk, a lot
Francesco
You can use the master WhitePage.ss template with several page types by extending your WhitePage class. Then you can use the $Layout as normal to call your custom layout template.
WhitePage
class WhitePage extends SiteTree {
}
class WhitePage_Controller extends ContentController {
private static $allowed_actions = array(
);
public function init() {
parent::init();
}
}
CustomWhitePage
class CustomWhitePage extends WhitePage {
}
class CustomWhitePage_Controller extends WhitePage_Controller {
private static $allowed_actions = array(
);
public function init() {
parent::init();
}
}
In your themes/mytheme folder or mysite folder create your templates like so:
templates/Page.ss
templates/WhitePage.ss
templates/Layout/Page.ss
templates/Layout/WhitePage.ss
templates/Layout/CustomWhitePage.ss
Your Layout/WhitePage.ss and Layout/CustomWhitePage.ss will use the templates/WhitePage.ss parent template while any page that extends Page will use templates/Page.ss.
Make sure you call ?flush=all for your templates to be loaded the first time through.

Silverstripe additional More options action

Wondering if it was possible to add additional actions when editing a page to the More options menu in Silverstripe 3.1
Using the below sample, I have added an additional FormAction which I can see when editing an page. But where do I actually add the "custom_action" method?
class CustomPage extends SiteTree {
function getCMSActions(){
$actions = parent::getCMSActions();
$actions->addFieldToTab(
'ActionMenus.MoreOptions',
new FormAction('custom_action', 'Custom Action')
);
return $actions;
}
}
class CustomPage_Controller extends ContentController {
public function init() {
parent::init();
if(!Member::currentUserID()) {
die();
}
}
}

Resources