Skip to content

Commit

Permalink
Merge branch 'master' of https://github.com/MajorVictory/Whetstone in…
Browse files Browse the repository at this point in the history
…to master

OceanBlues: Added 'classic' colors from version 1.0.0
OceanBlues: Fixed some color assignments for sidebar text and window text.
OceanBlues: Added some text shadows to be covered by the Highlight Color value.
  • Loading branch information
MajorVictory committed Sep 27, 2020
2 parents 845d9f2 + 6f36a1f commit cfdcd85
Show file tree
Hide file tree
Showing 13 changed files with 838 additions and 330 deletions.
4 changes: 1 addition & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -62,9 +62,7 @@ Contact me via discord, make a bug report, or submit a pull request if you want

## Screenshots

Comes with a prebuilt style: OceanBlues

![](images/OceanBlues-Preview.jpg)
![](images/MainPreview-9-26-2020.jpg)

![](images/OceanBlues-PF2e-Support-9-20-2020.jpg)

Expand Down
Binary file added images/MainPreview-9-26-2020.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
17 changes: 14 additions & 3 deletions modules/WhetstoneCoreConfig.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,20 @@ import {WhetstoneThemes} from './WhetstoneThemes.js';
* An interface for storing and retrieving settings for Whetstone core
*/
export class WhetstoneCoreConfig {
constructor() {
this.presets;
this.addMenuButton = true;
this.Whetstone = true;
}
/**
* get the default values of any registered settings
* @return {Object} key:value pairs denoting the default values
*/
static get getDefaults() {
return {
addMenuButton: true
presets: {},
addMenuButton: true,
Whetstone: true
};
}

Expand All @@ -31,6 +38,10 @@ export class WhetstoneCoreConfig {
* @param {Object} options key:value pairs of settings
*/
static apply(options) {
this.presets = options.presets || {};
this.addMenuButton = options.addMenuButton;
this.Whetstone = options.Whetstone;

WhetstoneThemes.toggleConfigButton(options.addMenuButton);
game.settings.set('Whetstone', 'addMenuButton', options.addMenuButton);

Expand All @@ -49,15 +60,15 @@ export class WhetstoneCoreConfig {

// deactivate all themes
for (let i = 0, len = deactivate.length; i < len; ++i) {
game.Whetstone.themes.deactivate(deactivate[i]);
game.Whetstone.themes.get(deactivate[i]).deactivate();
}

// sort by priority first, then name in alphabetical
activate.sort((a, b) => (a.priority > b.priority ? 1 : (a.priority === b.priority ? (a.name > b.name ? 1 : -1) : -1)));

// activate all active themes
for (let i = 0, len = activate.length; i < len; ++i) {
game.Whetstone.themes.activate(activate[i].name);
game.Whetstone.themes.get(deactivate[i]).activate();
}
}
}
13 changes: 10 additions & 3 deletions modules/WhetstoneCoreConfigDialog.js
Original file line number Diff line number Diff line change
Expand Up @@ -48,9 +48,16 @@ export class WhetstoneCoreConfigDialog extends FormApplication {

const theme = duplicate(m.options);
theme.active = isActive;
theme.dependencies = Object.entries(theme.dependencies).length ? theme.dependencies : '';
theme.systems = Object.entries(theme.systems).length ? theme.systems : '';
theme.compatible = Object.entries(theme.compatible).length ? theme.compatible : '';
theme.conflicts = Object.entries(theme.conflicts).length ? theme.conflicts : '';
return arr.concat([theme]);
}, []);

// sort by priority first, then name in alphabetical
themes.sort((a, b) => (a.priority > b.priority ? 1 : (a.priority === b.priority ? (a.name > b.name ? 1 : -1) : -1)));

storedOptions.counts = counts;
storedOptions.themes = themes;
storedOptions.expanded = this._expanded;
Expand All @@ -66,7 +73,7 @@ export class WhetstoneCoreConfigDialog extends FormApplication {

// Update setting data
const s = duplicate(setting);
s.value = this.reset ? s.default : game.settings.get('Whetstone', s.key);
s.value = this.reset ? s.default : JSON.parse(game.settings.get('Whetstone', s.key));
s.isColor = ['color', 'shades'].includes(s.color);
s.type = setting.type instanceof Function ? setting.type.name : 'String';
s.isCheckbox = setting.type === Boolean;
Expand Down Expand Up @@ -132,9 +139,9 @@ export class WhetstoneCoreConfigDialog extends FormApplication {
const theme = game.Whetstone.themes.get(moduleid);
const menuname = theme.data.dialog || `${moduleid}.${theme.name}`;

const menu = game.Whetstone.settings.menus.get(menuname);
const menu = game.Whetstone.settings.menus.get(`Whetstone.menus.${menuname}`);
if (!menu) return ui.notifications.error('No submenu found for the provided key');
const app = new menu.type({theme: theme.name});
const app = new menu.type({theme: theme.name, colorTheme: ''});
return app.render(true);
}

Expand Down
215 changes: 213 additions & 2 deletions modules/WhetstoneTheme.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import {WhetstoneThemes} from './WhetstoneThemes.js';
/**
* The EntityCollection of Whetstone theme entities.
* @extends {EntityCollection}
Expand All @@ -6,6 +7,11 @@
* let theme = game.Whetstone.themes.get(themeid);
*/
export class WhetstoneTheme extends Entity {
constructor(...args) {
super(...args);
this.dialog;
}

/**
* Configure the attributes of the WhetstoneTheme Entity
*
Expand All @@ -22,10 +28,215 @@ export class WhetstoneTheme extends Entity {
};
}

/**
* Enable the theme by writing variables and inserting stylesheets
* @param {Object} values An object with key:value pairs of variables to override when activating
*/
activate() {
const allowed = Hooks.call('onThemeActivate', this);
if (allowed === false) return;

this.data.active = true;

const systemStyles = this.getSubStyles(game.system.id, game.system.data.version);
const allStyles = this.getCoreStyles().concat(systemStyles);
const themeVariables = this.getVariableValues();

// gather and write any overriden css variables
Object.keys(themeVariables).forEach((k) => {
WhetstoneThemes.writeVariable(k, themeVariables[k]);
});

// add stylesheets
for (let i = 0, len = allStyles.length; i < len; ++i) {
WhetstoneThemes.addStyle(allStyles[i]);
}
}

/**
* Disable the theme removing variables and stylesheets
*/
deactivate() {
const allowed = Hooks.call('onThemeDeactivate', this);
if (allowed === false) return;

this.data.active = false;
this.data.variables.forEach((cssVar) => {

const themeSetting = game.Whetstone.settings.settings.get(`Whetstone.themes.${this.name}.variables.${cssVar.name}`);

WhetstoneThemes.writeVariable(cssVar.name, '');

if(themeSetting.color === 'shades') {
Object.keys(WhetstoneThemes.getShades()).forEach((v, k) => {
WhetstoneThemes.writeVariable(k, '');
});
}
});

const systemStyles = this.getSubStyles('all', 'all', false);
const allStyles = this.getCoreStyles().concat(systemStyles);

// remove stylesheets
for (let i = 0, len = allStyles.length; i < len; ++i) {
WhetstoneThemes.removeStyle(allStyles[i]);
}
}

/**
* Get an array of core styleshet filenames for a given theme
* @return {Array.String} An array of stylsheet filenames
*/
getCoreStyles() {
return this.data.styles;
}

/**
* Get an array of stylesheets to load
* @param {String} system (optional) system id, can be 'all'
* @param {String} version (optional) specific version, can be 'all'
* @param {Boolean} checkEnabled true: only return enabled styles, false: return all matching styles
* @return {Array.<String>} a list of stylesheet paths
**/
getSubStyles(system = '', version = '', checkEnabled = true) {
let styles = [];
for (const substyleName in this.data.substyles) {
const substyle = this.data.substyles[substyleName];

const enabled = checkEnabled ? game.Whetstone.settings.get(`${this.name}.substyles`, substyleName) : true;

if ((substyle.system === system || system === 'all')
&& (substyle.version === String(version) || isNewerVersion(version, substyle.version) || version === 'all')
&& enabled) {
styles = styles.concat(substyle.styles);
} else if (substyle.system === system && !substyle.version && enabled) {
styles = styles.concat(substyle.styles);
} else if (!substyle.system && !substyle.version && enabled) {
styles = styles.concat(substyle.styles);
}
}
return styles;
}

getVariableValues(colorTheme = '', values = {}) {

let selectedColorTheme = colorTheme || game.Whetstone.settings.get(`${this.name}.settings`, 'colorTheme') || this.data.colorTheme || '';

const currentColorTheme = this.data.colorThemes.filter(t => t.id === selectedColorTheme)[0];
const colorThemeValues = currentColorTheme ? currentColorTheme.values : {};
let returnValues = {
'colorThemeData': currentColorTheme,
'colorThemeID': selectedColorTheme
};

this.data.variables.forEach((cssVar) => {
const themeSetting = game.Whetstone.settings.settings.get(`Whetstone.themes.${this.name}.variables.${cssVar.name}`);

// check `values` from arguments for further overrides
let overrideValue = Object.keys(values).filter(k => k.includes(cssVar.name))[0];
overrideValue = overrideValue ? values[overrideValue] : '';

// get current value from storage
const storedValue = game.Whetstone.settings.get(this.name, `variables.${cssVar.name}`) || '';

// get colortheme value
let colorThemeValue = Object.keys(colorThemeValues).filter(k => k.includes(cssVar.name))[0];
colorThemeValue = colorThemeValue ? colorThemeValues[colorThemeValue] : '';


let writeValue = '';
if (colorTheme) {
writeValue = overrideValue || colorThemeValue || storedValue || themeSetting.default || '';

// make sure there is at least a value: override -> stored -> preset -> default -> nothing
} else {
writeValue = overrideValue || storedValue || colorThemeValue || themeSetting.default || '';
}

returnValues[cssVar.name] = writeValue;

if(themeSetting.color === 'shades') {

const shades = WhetstoneThemes.getShades(writeValue);

Object.keys(shades).forEach((k) => {
returnValues[k] = shades[k];
});
}
});
return returnValues
}

storeColorTheme(colorThemeData) {

let settings = game.Whetstone.settings.get('Whetstone', 'presets');
// triggers if loading an old config <= v1.0.2
if (!settings) settings = {};

this.data.colorThemes.push(colorThemeData);
settings[`${this.name}.presets.${colorThemeData.id}`] = colorThemeData;

game.Whetstone.settings.set('Whetstone', 'presets', settings);
}

loadColorThemes() {

let settings = game.Whetstone.settings.get('Whetstone', 'presets');
// triggers if loading an old config <= v1.0.2
if (!settings) settings = {};

Object.keys(settings).forEach((k) => {
if (k.includes(`${this.name}.presets.`)) {
this.data.colorThemes.push(settings[k]);
}
});
}

removeColorTheme(colorThemeID) {

const settings = game.Whetstone.settings.get('Whetstone', 'presets');
// triggers if loading an old config <= v1.0.2
if (!settings) settings = {};

// rebuild storage data
const keyname = `${this.name}.presets.${colorThemeID}`;
let newData = {};
Object.keys(settings).forEach((k) => {
if (k !== keyname || !settings[k].custom) {
newData[k] = settings[k];
}
});
game.Whetstone.settings.set('Whetstone', 'presets', newData);

// rebuild local object data
const newList = this.data.colorThemes.filter(t => (t.id !== colorThemeID || !t.custom));
this.data.colorThemes = newList;
this.data.colorTheme = '';
}

/**
* Import data and update this entity
* @param {String} json JSON data string
* @return {Promise.<Entity>} The updated Entity
*/
importFromJSON(json) {
const data = JSON.parse(json);
delete data._id;
const newID = data.id;
this.storeColorTheme(data);

if (this.dialog) {
this.dialog._colorTheme = newID;
this.dialog._userValues = [];
this.dialog.render();
}
return this;
}

/** @override */
async delete(options) {
if (this.active) {
game.Whetstone.themes.deactivate(this.name);
if (this.data.active) {
this.deactivate();
}
return super.delete(options);
}
Expand Down
Loading

0 comments on commit cfdcd85

Please sign in to comment.