src/Page/Locator.php
<?php
namespace Dynamic\Locator\Page;
use Dynamic\Locator\Model\LocationCategory;
use Dynamic\SilverStripeGeocoder\AddressDataExtension;
use SilverStripe\Core\Manifest\ModuleResourceLoader;
use SilverStripe\Forms\FieldList;
use SilverStripe\Forms\GridField\GridFieldAddExistingAutocompleter;
use SilverStripe\Forms\HeaderField;
use SilverStripe\Forms\OptionsetField;
use SilverStripe\Forms\GridField\GridField;
use SilverStripe\Forms\GridField\GridFieldConfig_RelationEditor;
use SilverStripe\Lumberjack\Model\Lumberjack;
use SilverStripe\ORM\DataList;
use SilverStripe\ORM\ArrayList;
use SilverStripe\Core\Config\Config;
use SilverStripe\View\ArrayData;
use Symbiote\GridFieldExtensions\GridFieldAddExistingSearchButton;
/**
* Class Locator
*
* @property bool $AutoGeocode
* @property bool $ModalWindow
* @property string $Unit
* @method Categories|ManyManyList $Categories
*/
class Locator extends \Page
{
/**
* @var string
*/
private static $singular_name = 'Locator';
/**
* @var string
*/
private static $plural_name = 'Locators';
/**
* @var string
*/
private static $description = 'Display locations on a map';
/**
* @var array
*/
private static $db = [
'Unit' => 'Enum("m,km","m")',
];
/**
* @var array
*/
private static $many_many = [
'Categories' => LocationCategory::class,
];
/**
* @var string
*/
private static $table_name = 'Locator';
/**
* @var string
*/
private static $location_class = LocationPage::class;
/**
* @var string[]
*/
private static $extensions = [
Lumberjack::class,
];
/**
* @var string[]
*/
private static $allowed_children = [
LocationPage::class,
];
/**
* @return FieldList
*/
public function getCMSFields()
{
$this->beforeUpdateCMSFields(function ($fields) {
// Settings
$fields->addFieldsToTab('Root.Settings', [
HeaderField::create('DisplayOptions', 'Display Options', 3),
OptionsetField::create('Unit', 'Unit of measure', ['m' => 'Miles', 'km' => 'Kilometers']),
]);
// Filter categories
$config = GridFieldConfig_RelationEditor::create();
$config->removeComponentsByType(GridFieldAddExistingAutocompleter::class);
$config->addComponent(new GridFieldAddExistingSearchButton());
$categories = $this->Categories();
$categoriesField = GridField::create('Categories', 'Categories', $categories, $config)
->setDescription('only show locations from the selected category');
// Filter
$fields->addFieldsToTab('Root.Filter', [
HeaderField::create('CategoryOptionsHeader', 'Location Filtering', 3),
$categoriesField,
]);
});
return parent::getCMSFields();
}
/**
* @param array $filter
* @param array $filterAny
* @param array $exclude
* @param null|callable $callback
*
* @return DataList|ArrayList
*/
public static function get_locations($filter = [], $filterAny = [], $exclude = [], $callback = null)
{
$locationClass = Config::inst()->get(static::class, 'location_class');
$locations = $locationClass::get()->filter($filter)->exclude($exclude);
if (!empty($filterAny)) {
$locations = $locations->filterAny($filterAny);
}
if (!empty($exclude)) {
$locations = $locations->exclude($exclude);
}
if ($callback !== null && is_callable($callback)) {
$locations->filterByCallback($callback);
}
return $locations;
}
/**
* @return DataList
*/
public static function get_all_categories()
{
return LocationCategory::get();
}
/**
* @return bool
*/
public function getPageCategories()
{
return self::locator_categories_by_locator($this->ID);
}
/**
* @param int $id
*
* @return bool|
*/
public static function locator_categories_by_locator($id = 0)
{
if ($id == 0) {
return false;
}
/** @var Locator $locator */
if ($locator = static::get()->byID($id)) {
return $locator->getUsedCategories();
}
return false;
}
/**
* Gets the list of radii
*
* @return ArrayList
*/
public function getRadii()
{
$radii = [
'0' => '25',
'1' => '50',
'2' => '75',
'3' => '100',
];
$config_radii = $this->config()->get('radii');
if ($config_radii) {
$radii = $config_radii;
}
return $radii;
}
public function getRadiiArrayList()
{
$list = [];
foreach ($this->getRadii() as $radius) {
$list[] = new ArrayData([
'Radius' => $radius,
]);
}
return new ArrayList($list);
}
/**
* Gets the limit of locations
* @return mixed
*/
public function getLimit()
{
return $this->config()->get('limit');
}
/**
* Gets if the radius drop down should be shown
* @return mixed
*/
public function getShowRadius()
{
return $this->config()->get('show_radius');
}
/**
* @return mixed
*/
public function getUsedCategories()
{
return $this->Categories()->filter([
'LocationSet.ID:GreaterThan' => 0,
]);
}
/**
* Gets the path of the info window template
*
* @return string
*/
public function getInfoWindowTemplate()
{
return ModuleResourceLoader::singleton()->resolveURL(
Config::inst()->get(
static::class,
'infoWindowTemplate'
)
);
}
/**
* Gets the path of the list template
*
* @return string
*/
public function getListTemplate()
{
return ModuleResourceLoader::singleton()->resolveURL(
Config::inst()->get(
static::class,
'listTemplate'
)
);
}
/**
* @return null|string
*/
public function getMapStyle()
{
return AddressDataExtension::getMapStyleJSON();
}
public function getMapStyleJSONPath()
{
return AddressDataExtension::getMapStyleJSONPath();
}
/**
* @return null|string
*/
public function getMarkerIcon()
{
return AddressDataExtension::getIconImage();
}
/**
* @return string
*/
public function getLumberjackTitle()
{
return _t(__CLASS__ . '.LumberjackTitle', 'Locations');
}
}