Version 5.0.0 release
This commit is contained in:
1 parent
90e8c7e903
commit
a3a4a9ccbd
651 files changed
+7275
-9481
No files matched your search
+119
-38
@@ -35,6 +35,7 @@ use IPS\Member\Group;
|
||||
use IPS\Node\Model;
|
||||
use IPS\Patterns\ActiveRecord;
|
||||
use IPS\Patterns\ActiveRecordIterator;
|
||||
use IPS\Theme\Editor\Category;
|
||||
use IPS\Theme\Editor\Setting;
|
||||
use IPS\Theme\SandboxedTemplate;
|
||||
use IPS\Theme\Dev\Theme as DevTheme;
|
||||
@@ -755,7 +756,6 @@ class Theme extends Model
|
||||
/* Are these core IPS apps? If so, we store these in the static directory and won't be in the resource map */
|
||||
if( in_array( $app, IPS::$ipsApps ) and str_replace( '/', '', $path ) !== 'custom' )
|
||||
{
|
||||
|
||||
$url = Url::internal( 'static/resources/' . $app . '_' . static::makeBuiltTemplateLookupHash($app, $location, $path) . '_' .$name, 'static' );
|
||||
|
||||
if( $noProtocol )
|
||||
@@ -766,7 +766,6 @@ class Theme extends Model
|
||||
return $url;
|
||||
}
|
||||
|
||||
|
||||
if ( in_array( $key, array_keys( $this->resource_map ) ) )
|
||||
{
|
||||
if ( $this->resource_map[ $key ] === NULL )
|
||||
@@ -777,7 +776,7 @@ class Theme extends Model
|
||||
{
|
||||
$url = File::get( 'core_Theme', $this->resource_map[ $key ] )->url;
|
||||
|
||||
if( $noProtocol and $url instanceof Url)
|
||||
if( $noProtocol and $url instanceof Url )
|
||||
{
|
||||
$url = $url->setScheme(NULL);
|
||||
}
|
||||
@@ -816,7 +815,7 @@ class Theme extends Model
|
||||
|
||||
static::unlock( $flagKey );
|
||||
|
||||
if( in_array( $app, IPS::$ipsApps ) )
|
||||
if( in_array( $app, IPS::$ipsApps ) and $resource['resource_path'] !== '/custom/' )
|
||||
{
|
||||
$url = rtrim( Settings::i()->base_url, '/' ) . '/' . $resourceMap[ $key ];
|
||||
}
|
||||
@@ -1011,33 +1010,6 @@ class Theme extends Model
|
||||
}
|
||||
}
|
||||
|
||||
if ( $editorData = json_decode( $obj->_data['theme_editor_data'], true ) )
|
||||
{
|
||||
$obj->_data['theme_editor_data'] = $editorData;
|
||||
|
||||
if ( ! isset( $obj->_data['theme_editor_data']['header'] ) )
|
||||
{
|
||||
$obj->_data['theme_editor_data']['header'] = [
|
||||
'logo' => 4,
|
||||
'navigation' => 5,
|
||||
'user' => 6,
|
||||
'breadcrumb' => 7,
|
||||
'search' => 9,
|
||||
];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Set up defaults */
|
||||
$obj->_data['theme_editor_data'] = [ 'header' => [
|
||||
'logo' => 4,
|
||||
'navigation' => 5,
|
||||
'user' => 6,
|
||||
'breadcrumb' => 7,
|
||||
'search' => 9,
|
||||
] ];
|
||||
}
|
||||
|
||||
if ( ! is_array( $obj->_data['resource_map'] ) )
|
||||
{
|
||||
if( $obj->id > 0 )
|
||||
@@ -1142,6 +1114,24 @@ class Theme extends Model
|
||||
*/
|
||||
public function getCustomCssForOutput(): string
|
||||
{
|
||||
/* Use pending changes, if we have any */
|
||||
if ( Member::loggedIn()->isEditingTheme() and isset( Request::i()->cookie['theme_editor_vars'] ) and $cookie = json_decode( Request::i()->cookie['theme_editor_vars'], true ) )
|
||||
{
|
||||
if( array_key_exists( 'custom', $cookie ) )
|
||||
{
|
||||
/* Compile the pending CSS but don't store it */
|
||||
$functionName = "css_" . uniqid();
|
||||
static::makeProcessFunction( static::fixResourceTags( (string) $cookie['custom'], 'front' ), $functionName, '', FALSE, TRUE );
|
||||
|
||||
$fqFunc = 'IPS\\Theme\\'. $functionName;
|
||||
$content = static::minifyCss( $fqFunc() );
|
||||
|
||||
/* Replace any <fileStore.xxx> tags in the CSS */
|
||||
Output::i()->parseFileObjectUrls( $content );
|
||||
return $content;
|
||||
}
|
||||
}
|
||||
|
||||
$key = $this->_id . '_theme_editor_custom_css';
|
||||
if ( ! isset( Store::i()->$key ) )
|
||||
{
|
||||
@@ -1307,6 +1297,43 @@ class Theme extends Model
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
* Store the default so that we can determine if this is customized or not
|
||||
*
|
||||
* @var array[]
|
||||
*/
|
||||
public static array $defaultThemeEditorData = [
|
||||
'header' => [
|
||||
'logo' => 4,
|
||||
'navigation' => 5,
|
||||
'user' => 6,
|
||||
'breadcrumb' => 7,
|
||||
'search' => 9,
|
||||
]
|
||||
];
|
||||
|
||||
/**
|
||||
* @return array
|
||||
*/
|
||||
public function get_theme_editor_data() : array
|
||||
{
|
||||
$editorData = isset( $this->_data['theme_editor_data'] ) ? json_decode( $this->_data['theme_editor_data'], true ) : [];
|
||||
if( !isset( $editorData['header'] ) )
|
||||
{
|
||||
$editorData['header'] = static::$defaultThemeEditorData['header'];
|
||||
}
|
||||
return $editorData;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mixed $val
|
||||
* @return void
|
||||
*/
|
||||
public function set_theme_editor_data( mixed $val ) : void
|
||||
{
|
||||
$this->_data['theme_editor_data'] = is_array( $val ) ? json_encode( $val ) : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* [Node] Return the custom badge for each row
|
||||
*
|
||||
@@ -1440,6 +1467,9 @@ class Theme extends Model
|
||||
/* Copy logos */
|
||||
$this->logo_data = NULL;
|
||||
$this->copyLogosFromSet( $originalId );
|
||||
|
||||
/* Copy custom settings and categories */
|
||||
$this->copyEditorSettings( $originalId );
|
||||
|
||||
Session::i()->log( 'acplogs__themeset_created', array( sprintf( Member::loggedIn()->language()->get( 'theme_clone_copy_of' ), Member::loggedIn()->language()->get( 'core_theme_set_title_' . $originalId ) ) => FALSE ) );
|
||||
}
|
||||
@@ -2053,6 +2083,46 @@ class Theme extends Model
|
||||
$this->save();
|
||||
}
|
||||
|
||||
/**
|
||||
* Copy the editor settings and categories from the specified theme
|
||||
*
|
||||
* @param int $id
|
||||
* @return void
|
||||
*/
|
||||
public function copyEditorSettings( int $id ) : void
|
||||
{
|
||||
$categoryMapping = [];
|
||||
foreach( new ActiveRecordIterator(
|
||||
Db::i()->select( '*', Category::$databaseTable, [ 'cat_set_id=?', $id ], 'cat_parent, cat_position' ),
|
||||
Category::class
|
||||
) as $cat )
|
||||
{
|
||||
/* Copy the category and change the theme ID */
|
||||
$newCategory = clone $cat;
|
||||
$newCategory->set_id = $this->_id;
|
||||
if( $newCategory->parent and array_key_exists( $cat->parent, $categoryMapping ) )
|
||||
{
|
||||
$newCategory->parent = $categoryMapping[ $cat->parent ];
|
||||
}
|
||||
$newCategory->save();
|
||||
|
||||
/* Map the category IDs, we'll need them later */
|
||||
$categoryMapping[ $cat->id ] = $newCategory->id;
|
||||
}
|
||||
|
||||
/* Now loop through the settings */
|
||||
foreach( new ActiveRecordIterator(
|
||||
Db::i()->select( '*', Setting::$databaseTable, [ 'setting_set_id=?', $id ], 'setting_position' ),
|
||||
Setting::class
|
||||
) as $setting )
|
||||
{
|
||||
$newSetting = clone $setting;
|
||||
$newSetting->set_id = $this->_id;
|
||||
$newSetting->category_id = $categoryMapping[ $newSetting->category_id ] ?? 0;
|
||||
$newSetting->save();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Install the theme editor settings for this theme
|
||||
*
|
||||
@@ -2742,7 +2812,10 @@ EOF;
|
||||
{
|
||||
foreach( $cookie as $group => $vars )
|
||||
{
|
||||
$customValues = array_merge( $customValues, $vars );
|
||||
if( is_array( $vars ) )
|
||||
{
|
||||
$customValues = array_merge( $customValues, $vars );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2839,7 +2912,17 @@ EOF;
|
||||
/* Parse the value based on the setting type */
|
||||
try
|
||||
{
|
||||
$value = Setting::load( $key, 'setting_key' )->parsedValue( $value );
|
||||
$setting = Setting::load( $key, 'setting_key' );
|
||||
$value = $setting->parsedValue( $value );
|
||||
if( $setting->type == Setting::SETTING_IMAGE )
|
||||
{
|
||||
if( empty( $value ) )
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
$value = "url('" . $value . "')";
|
||||
}
|
||||
}
|
||||
catch( OutOfRangeException ){}
|
||||
|
||||
@@ -3894,9 +3977,7 @@ EOF;
|
||||
if( $functionName == 'theme_core_front_global_footer' or ( $functionName == 'footer' and $app == 'core' and $location == 'front' and $group == 'global' ) )
|
||||
{
|
||||
$content = $content . "\n<p class='ipsCopyright'>
|
||||
<span class='ipsCopyright__user'>{lang=\"copyright_line_value\"}</span>
|
||||
{{if !\$licenseData = \IPS\IPS::licenseKey() or !isset(\$licenseData['products']['copyright']) or !\$licenseData['products']['copyright']}}<a rel='nofollow' title='Invision Community' href='https://www.invisioncommunity.com/'>Powered by <span translate='no'>Invision Community</span></a>{{endif}}
|
||||
</p>";
|
||||
<span class='ipsCopyright__user'>{lang=\"copyright_line_value\"}</span></p>";
|
||||
}
|
||||
|
||||
/* Expand hook points */
|
||||
@@ -4607,7 +4688,7 @@ PHP;
|
||||
$this->custom_css = '';
|
||||
$this->css_variables = null;
|
||||
$this->view_options = null;
|
||||
$this->theme_editor_data = json_encode( $data );
|
||||
$this->theme_editor_data = $data;
|
||||
$this->save();
|
||||
}
|
||||
|
||||
@@ -4746,7 +4827,7 @@ PHP;
|
||||
*/
|
||||
public function isCustomized(): bool
|
||||
{
|
||||
if ( is_array( $this->set_theme_editor_data ) and count( $this->set_theme_editor_data ) )
|
||||
if( $this->theme_editor_data !== static::$defaultThemeEditorData )
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user