Skip to content
This repository was archived by the owner on Jul 28, 2025. It is now read-only.

Commit 878c6e8

Browse files
committed
Merge branch '57-fr-wrap-field-with-markdown-before-render'
2 parents 8bd620e + c5b2c28 commit 878c6e8

File tree

9 files changed

+214
-6
lines changed

9 files changed

+214
-6
lines changed

src/Settings.ts

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,18 +8,25 @@ import { columns_settings_section } from "settings/ColumnsSection";
88
import { folder_settings_section } from "settings/FolderSection";
99
import { StyleClasses } from "helpers/Constants";
1010
import { SettingHandlerResponse } from "settings/handlers/AbstractSettingHandler";
11+
import { media_settings_section } from "settings/MediaSection";
1112

1213
interface GlobalSettings {
1314
enable_debug_mode: boolean;
1415
logger_level_info: string;
1516
}
1617

18+
export interface MediaSettings {
19+
enable_media_view: boolean;
20+
width: number;
21+
height: number;
22+
}
1723
export interface LocalSettings {
1824
enable_show_state: boolean;
1925
group_folder_column: string;
2026
remove_field_when_delete_column: boolean;
2127
show_metadata_created: boolean;
2228
show_metadata_modified: boolean;
29+
media_settings: MediaSettings;
2330
}
2431

2532
export interface DatabaseSettings {
@@ -37,7 +44,12 @@ export const DEFAULT_SETTINGS: DatabaseSettings = {
3744
remove_field_when_delete_column: false,
3845
group_folder_column: '',
3946
show_metadata_created: false,
40-
show_metadata_modified: false
47+
show_metadata_modified: false,
48+
media_settings: {
49+
enable_media_view: true,
50+
width: 100,
51+
height: 100
52+
}
4153
}
4254
};
4355

@@ -107,6 +119,8 @@ export class SettingsManager {
107119
}
108120
/** Columns section */
109121
columns_settings_section(settingHandlerResponse);
122+
/** Media section */
123+
media_settings_section(settingHandlerResponse);
110124
/** Developer section */
111125
developer_settings_section(settingHandlerResponse);
112126
}

src/components/markdown/MarkdownRenderer.tsx

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,13 @@ export async function renderMarkdown(
1111
domElement: HTMLDivElement
1212
): Promise<HTMLDivElement> {
1313
try {
14+
if (isValidHttpUrl(markdownString, view)) {
15+
const { height, width } = view.diskConfig.yaml.config.media_settings;
16+
// TODO option to generate Iframes
17+
//markdownString = `<div class=iframe-container> <iframe width="427" height="240" src="${markdownString}" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen></iframe> </div>`;
18+
markdownString = `![embedded link|${height}x${width}](${markdownString})`;
19+
}
20+
1421
await MarkdownRenderer.renderMarkdown(
1522
markdownString,
1623
domElement,
@@ -119,3 +126,18 @@ function handleVideo(el: HTMLElement, file: TFile, view: DatabaseView) {
119126

120127
el.addClasses(["media-embed", "is-loaded"]);
121128
}
129+
130+
function isValidHttpUrl(urlCandidate: string, view: DatabaseView) {
131+
let url;
132+
133+
try {
134+
url = new URL(urlCandidate);
135+
} catch (_) {
136+
return false;
137+
}
138+
139+
return (
140+
(url.protocol === "http:" || url.protocol === "https:") &&
141+
view.diskConfig.yaml.config.media_settings.enable_media_view
142+
);
143+
}

src/parsers/handlers/marshall/AbstractYamlPropertyHandler.ts

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import { DatabaseYaml } from "cdm/DatabaseModel";
21
import { YamlHandler, YamlHandlerResponse } from "cdm/MashallModel";
32

43

src/parsers/handlers/marshall/MarshallConfigHandler.ts

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
import { YamlHandlerResponse } from 'cdm/MashallModel';
22
import { AbstractYamlHandler } from 'parsers/handlers/marshall/AbstractYamlPropertyHandler';
3-
import { LocalSettings } from 'Settings';
43

54
export class MarshallConfigHandler extends AbstractYamlHandler {
65
handlerName: string = 'configuration';
@@ -37,6 +36,33 @@ export class MarshallConfigHandler extends AbstractYamlHandler {
3736
this.addError(`There was not show_metadata_modified key in yaml. Default will be loaded`);
3837
this.localYaml.config.show_metadata_modified = false;
3938
}
39+
40+
// if media_settings is not defined, load default
41+
if (checkNullable(handlerResponse.yaml.config.media_settings)) {
42+
this.addError(`There was not media_settings key in yaml. Default will be loaded`);
43+
this.localYaml.config.media_settings = {
44+
enable_media_view: true,
45+
width: 100,
46+
height: 100
47+
};
48+
} else {
49+
// otherwise, check if the media_settings fields are defined
50+
if (checkNullable(handlerResponse.yaml.config.media_settings.enable_media_view)) {
51+
this.addError(`There was not enable_media_view key in yaml. Default will be loaded`);
52+
this.localYaml.config.media_settings.enable_media_view = true;
53+
}
54+
55+
if (checkNullable(handlerResponse.yaml.config.media_settings.width)) {
56+
this.addError(`There was not width key in yaml. Default will be loaded`);
57+
this.localYaml.config.media_settings.width = 100;
58+
}
59+
60+
if (checkNullable(handlerResponse.yaml.config.media_settings.height)) {
61+
this.addError(`There was not height key in yaml. Default will be loaded`);
62+
this.localYaml.config.media_settings.height = 100;
63+
}
64+
65+
}
4066
}
4167
return this.goNext(handlerResponse);
4268
}

src/parsers/handlers/unmarshall/UnmarshallConfigHandler.ts

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,16 @@ export class UnmarshallConfigHandler extends AbstractDiskHandler {
1010
// Lvl1: config
1111
this.localDisk.push(`${this.handlerName}:`);
1212
Object.entries(config).forEach(([key, value]) => {
13-
// Lvl2: config properties
14-
this.localDisk.push(`${YAML_INDENT.repeat(1)}${key}: ${value}`);
13+
if (typeof value === 'object') {
14+
this.localDisk.push(`${YAML_INDENT.repeat(1)}${key}:`);
15+
Object.entries(value).forEach(([key, value]) => {
16+
// Lvl3: config properties
17+
this.localDisk.push(`${YAML_INDENT.repeat(2)}${key}: ${value}`);
18+
});
19+
} else {
20+
// Lvl2: config properties
21+
this.localDisk.push(`${YAML_INDENT.repeat(1)}${key}: ${value}`);
22+
}
1523
});
1624
return this.goNext(handlerResponse);
1725
}

src/settings/MediaSection.ts

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
import { add_setting_header } from 'settings/SettingsComponents';
2+
import { SettingHandler, SettingHandlerResponse } from 'settings/handlers/AbstractSettingHandler';
3+
import { MediaToggleHandler } from 'settings/handlers/media/MediaToggleHandler';
4+
import { MediaDimensionsHandler } from 'settings/handlers/media/MediaDimensionsHandler';
5+
6+
/**
7+
* developer settings section
8+
*/
9+
export function media_settings_section(settingHandlerResponse: SettingHandlerResponse): SettingHandlerResponse {
10+
const media_section = settingHandlerResponse.containerEl.createDiv("configuration-section-container-media");
11+
// title of the section
12+
add_setting_header(media_section, "Embedded media adjustments", 'h3');
13+
// section settings
14+
const handlers = getHandlers();
15+
let i = 1;
16+
while (i < handlers.length) {
17+
handlers[i - 1].setNext(handlers[i]);
18+
i++;
19+
}
20+
21+
settingHandlerResponse.containerEl = media_section;
22+
return handlers[0].handle(settingHandlerResponse);
23+
}
24+
25+
/**
26+
* Obtain all classes than extends from AbstractHandler
27+
*/
28+
function getHandlers(): SettingHandler[] {
29+
return [
30+
new MediaToggleHandler(),
31+
new MediaDimensionsHandler(),
32+
];
33+
}

src/settings/handlers/folder/FilterDataviewHandler.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ export class FilterDataviewHandler extends AbstractSettingsHandler {
2929
onClickAddPromise
3030
);
3131
view.diskConfig.yaml.filters.forEach((filter, index) => {
32-
const filterSetting = new Setting(containerEl)
32+
new Setting(containerEl)
3333
.addText(text => {
3434
text.setPlaceholder("name of field")
3535
.setValue(filter.field)
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
import { Setting } from "obsidian";
2+
import { AbstractSettingsHandler, SettingHandlerResponse } from "settings/handlers/AbstractSettingHandler";
3+
4+
export class MediaDimensionsHandler extends AbstractSettingsHandler {
5+
settingTitle: string = 'Choose dimensions of embeded media';
6+
handle(settingHandlerResponse: SettingHandlerResponse): SettingHandlerResponse {
7+
const { local, settingsManager, containerEl, view } = settingHandlerResponse;
8+
const media_settings = local ? view.diskConfig.yaml.config.media_settings : settingsManager.plugin.settings.local_settings.media_settings;
9+
if (media_settings.enable_media_view) {
10+
// Check if media_settings is enabled
11+
const dimensionSettings = new Setting(containerEl)
12+
.addText(text => {
13+
text.setPlaceholder("Height")
14+
.setValue(media_settings.height.toString())
15+
.onChange(async (value: string): Promise<void> => {
16+
// Common modifications of value
17+
const parsedNumber = Number(value);
18+
const validatedNumber = isNaN(parsedNumber) ? media_settings.height : parsedNumber;
19+
media_settings.height = validatedNumber;
20+
if (local) {
21+
// Persist changes in local config
22+
view.diskConfig.updateConfig('media_settings', media_settings);
23+
} else {
24+
// Persist changes in plugin settings
25+
const update_local_settings = settingsManager.plugin.settings.local_settings;
26+
update_local_settings.media_settings = media_settings;
27+
await settingsManager.plugin.updateSettings({
28+
local_settings: update_local_settings
29+
});
30+
}
31+
});
32+
}).addText(text => {
33+
text.setPlaceholder("Width")
34+
.setValue(media_settings.width.toString())
35+
.onChange(async (value: string): Promise<void> => {
36+
// Common modifications of value
37+
const parsedNumber = Number(value);
38+
const validatedNumber = isNaN(parsedNumber) ? media_settings.width : parsedNumber;
39+
media_settings.width = validatedNumber;
40+
if (local) {
41+
// Persist changes in local config
42+
view.diskConfig.updateConfig('media_settings', media_settings);
43+
} else {
44+
// Persist changes in plugin settings
45+
const update_local_settings = settingsManager.plugin.settings.local_settings;
46+
update_local_settings.media_settings = media_settings;
47+
await settingsManager.plugin.updateSettings({
48+
local_settings: update_local_settings
49+
});
50+
}
51+
});
52+
})
53+
if (local) {
54+
dimensionSettings.addExtraButton((cb) => {
55+
cb.setIcon("reset")
56+
.setTooltip("Restart default values")
57+
.onClick(async (): Promise<void> => {
58+
// Persist changes
59+
media_settings.width = settingsManager.settings.local_settings.media_settings.width;
60+
media_settings.height = settingsManager.settings.local_settings.media_settings.height;
61+
view.diskConfig.updateConfig('media_settings', media_settings);
62+
// Force refresh of settings
63+
settingsManager.reset(settingHandlerResponse);
64+
});
65+
});
66+
}
67+
}
68+
return this.goNext(settingHandlerResponse);
69+
}
70+
}
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import { add_toggle } from "settings/SettingsComponents";
2+
import { AbstractSettingsHandler, SettingHandlerResponse } from "settings/handlers/AbstractSettingHandler";
3+
export class MediaToggleHandler extends AbstractSettingsHandler {
4+
settingTitle: string = 'Enable media links';
5+
handle(settingHandlerResponse: SettingHandlerResponse): SettingHandlerResponse {
6+
const { settingsManager, containerEl, local, view } = settingHandlerResponse;
7+
// pass if modal opened from local settings
8+
const media_settings = local ? view.diskConfig.yaml.config.media_settings : settingsManager.plugin.settings.local_settings.media_settings;
9+
const media_togle_promise = async (value: boolean): Promise<void> => {
10+
media_settings.enable_media_view = value;
11+
// Check context to define correct promise
12+
if (local) {
13+
// Persist value
14+
view.diskConfig.updateConfig('media_settings', media_settings);
15+
} else {
16+
// switch media state on/off
17+
const update_local_settings = settingsManager.plugin.settings.local_settings;
18+
update_local_settings.media_settings = media_settings;
19+
// update settings
20+
await settingsManager.plugin.updateSettings({
21+
local_settings: update_local_settings
22+
});
23+
}
24+
// Force refresh of settings
25+
settingsManager.reset(settingHandlerResponse);
26+
}
27+
add_toggle(
28+
containerEl,
29+
this.settingTitle,
30+
"Enable/disable wrap media links with embedding content",
31+
media_settings.enable_media_view,
32+
media_togle_promise
33+
);
34+
return this.goNext(settingHandlerResponse);
35+
}
36+
}

0 commit comments

Comments
 (0)