diff --git a/.gitignore b/.gitignore index de7c3d1..f36d0a2 100644 --- a/.gitignore +++ b/.gitignore @@ -6,9 +6,6 @@ node_modules package-lock.json -# yarn -yarn.lock - *.js.map diff --git a/.hotreload b/.hotreload deleted file mode 100644 index e69de29..0000000 diff --git a/README.md b/README.md index 43497e5..ce90528 100644 --- a/README.md +++ b/README.md @@ -9,38 +9,26 @@ The plugin's view is enabled by clicking on the "Open Habitica Pane" option in t To sync your Habitica account, go to the settings page of the plugin and enter your user ID and API token credentials. ## Features ### Pane View -#### View stats (HP, XP, coins) -#### Views -Task Information: -- Title, description, subtasks - - Markdown and emoji support +#### View HP, XP, todos, dailies, and habits +[![Image from Gyazo](https://i.gyazo.com/4266d01941e71fef41819ea8a6b6592e.png)](https://gyazo.com/4266d01941e71fef41819ea8a6b6592e) +[![Image from Gyazo](https://i.gyazo.com/697a58b8e7ffd3df86a2944b6abbaa92.png)](https://gyazo.com/697a58b8e7ffd3df86a2944b6abbaa92) +- Tab for active/completed tasks -Tabs: -- To Do's - - Active/Completed -- Dailies - - Due/Not Due/Completed - - [![Image from Gyazo](https://i.gyazo.com/1966b17f954dcffa954922570e860a06.png)](https://gyazo.com/1966b17f954dcffa954922570e860a06) -- Habits - - [![Image from Gyazo](https://i.gyazo.com/280494e620fc91548838d5b29a62652b.png)](https://gyazo.com/280494e620fc91548838d5b29a62652b) -- Rewards -#### Interactivity -- Check off tasks/dailies in the view - - Can uncheck completed habits/todos - - [![Image from Gyazo](https://i.gyazo.com/efb858cd9d54f9d9df936da1bd5858ed.gif)](https://gyazo.com/efb858cd9d54f9d9df936da1bd5858ed) -- modify habit counters (+/-) +#### Check off tasks/dailies in the view, modify habit counters (+/-) +[![Image from Gyazo](https://i.gyazo.com/5759e12bc5267711c5e03485a6d72c2f.gif)](https://gyazo.com/5759e12bc5267711c5e03485a6d72c2f) +- Can uncheck completed habits/todos as shown above -### Settings - -The following two inputs help fetch your user data to be displayed in the Obsidian view: +## Settings - **Habitica User ID:** You can find this by clicking on the "User" icon in the top right of the Habitica webapp, "Settings", then "API" - **Habitica Token API:** You can find this by clicking on the "User" icon in the top right of the Habitica webapp, "Settings", then "API" -- **Show Task Descriptions:** Toggles whether description/notes for tasks will be shown or not -- **Show Subtasks:** Toggles whether subtasks for to do's/dailies will be shown or not + +The following two inputs help fetch your user data to be displayed in the Obsidian view. ## Roadmap +We will be implementing additional features including: +- Add/delete/customize tasks and habits +- View/claim rewards *Feel free to support us and donate!* Buy Me a Coffee at ko-fi.com - diff --git a/manifest.json b/manifest.json index 2ae5bfe..c9b0afa 100644 --- a/manifest.json +++ b/manifest.json @@ -1,7 +1,7 @@ { "id": "obsidian-habitica-integration", "name": "Habitica Sync", - "version": "1.0.2", + "version": "0.9.15", "minAppVersion": "0.9.12", "description": "This plugin helps integrate Habitica user tasks and stats into Obsidian", "author": "Leoh and Ran", diff --git a/package.json b/package.json index 37371e6..344ca09 100644 --- a/package.json +++ b/package.json @@ -1,51 +1,37 @@ { "name": "obsidian-habitica-integration", - "version": "1.0.0", + "version": "0.12.0", "description": "This plugin allows for Habitica integration into Obsidian", "main": "main.js", "scripts": { - "dev": "rollup --config rollup.config.mjs -w", - "build": "rollup --config rollup.config.mjs --environment BUILD:production", - "dev2": "obsidian-plugin dev src/main.ts" + "dev": "rollup --config rollup.config.js -w", + "build": "rollup --config rollup.config.js --environment BUILD:production" }, "keywords": [], "author": "Leonard and Ran", "license": "MIT", "devDependencies": { - "@rollup/plugin-commonjs": "^25.0.7", - "@rollup/plugin-json": "^6.1.0", - "@rollup/plugin-node-resolve": "^15.2.3", - "@rollup/plugin-typescript": "^11.1.6", - "@types/markdown-it": "^13.0.7", - "@types/markdown-it-emoji": "^2.0.4", - "@types/node": "^20.11.0", - "@types/node-emoji": "^1.8.2", - "@types/react": "^18.2.47", - "@types/react-dom": "^18.2.18", - "@types/react-tabs": "^5.0.4", - "@types/twemoji": "^13.1.1", - "css-loader": "^6.9.0", - "mini-css-extract-plugin": "^2.7.7", - "obsidian": "^1.4.11", - "obsidian-plugin-cli": "^0.0.5", - "rollup": "^4.9.4", - "style-loader": "^3.3.4", - "tslib": "^2.6.2", - "typescript": "^5.3.3", - "webpack": "^5.89.0" + "@rollup/plugin-commonjs": "^18.0.0", + "@rollup/plugin-node-resolve": "^11.2.1", + "@rollup/plugin-typescript": "^8.2.1", + "@types/node": "^14.14.37", + "@types/react": "^17.0.27", + "@types/react-dom": "^17.0.9", + "@types/react-tabs": "^2.3.3", + "css-loader": "^6.4.0", + "extract-text-webpack-plugin": "^2.1.2", + "obsidian": "^0.12.0", + "rollup": "^2.32.1", + "style-loader": "^3.3.0", + "tslib": "^2.2.0", + "typescript": "^4.2.4" }, "dependencies": { - "markdown-it": "^14.0.0", - "markdown-it-emoji": "^2.0.2", - "moment": "^2.30.1", - "node": "^21.2.0", - "node-emoji": "^2.1.3", - "node-fetch": "^3.3.2", - "react": "^18.2.0", - "react-dom": "^18.2.0", - "react-emoji-render": "^2.0.1", - "react-markdown": "^9.0.1", - "react-tabs": "^6.0.2", - "twemoji": "^14.0.2" + "node": "^16.10.0", + "node-fetch": "^3.0.0", + "react": "^17.0.2", + "react-dom": "^17.0.2", + "react-emoji-render": "^1.2.4", + "react-tabs": "^3.2.2" } } diff --git a/rollup.config.mjs b/rollup.config.js similarity index 92% rename from rollup.config.mjs rename to rollup.config.js index 1551460..8e28e8d 100644 --- a/rollup.config.mjs +++ b/rollup.config.js @@ -1,32 +1,30 @@ -import typescript from '@rollup/plugin-typescript'; -import {nodeResolve} from '@rollup/plugin-node-resolve'; -import commonjs from '@rollup/plugin-commonjs'; -import json from '@rollup/plugin-json'; - -const isProd = (process.env.BUILD === 'production'); - -const banner = -`/* -THIS IS A GENERATED/BUNDLED FILE BY ROLLUP -if you want to view the source visit the plugins github repository -*/ -`; - -export default { - input: 'src/main.ts', - output: { - dir: '.', - sourcemap: 'inline', - sourcemapExcludeSources: isProd, - format: 'cjs', - exports: 'default', - banner, - }, - external: ['obsidian'], - plugins: [ - typescript(), - nodeResolve({browser: true}), - commonjs(), - json(), - ] +import typescript from '@rollup/plugin-typescript'; +import {nodeResolve} from '@rollup/plugin-node-resolve'; +import commonjs from '@rollup/plugin-commonjs'; + +const isProd = (process.env.BUILD === 'production'); + +const banner = +`/* +THIS IS A GENERATED/BUNDLED FILE BY ROLLUP +if you want to view the source visit the plugins github repository +*/ +`; + +export default { + input: 'src/main.ts', + output: { + dir: '.', + sourcemap: 'inline', + sourcemapExcludeSources: isProd, + format: 'cjs', + exports: 'default', + banner, + }, + external: ['obsidian'], + plugins: [ + typescript(), + nodeResolve({browser: true}), + commonjs(), + ] }; \ No newline at end of file diff --git a/src/main.ts b/src/main.ts index b8eaff4..bdf0312 100644 --- a/src/main.ts +++ b/src/main.ts @@ -5,30 +5,23 @@ import { HabiticaSyncView, VIEW_TYPE} from "./view" interface HabiticaSyncSettings { userID: string apiToken: string - showTaskDescription: boolean - showSubTasks: boolean - dueDateFormat: string } const DEFAULT_SETTINGS: Partial = { userID: "", - apiToken: "", - showTaskDescription: true, - showSubTasks: true, - dueDateFormat: "DD-MM-YYYY" + apiToken: "" } export default class HabiticaSync extends Plugin { settings: HabiticaSyncSettings; view: HabiticaSyncView; async onload() { - console.log("load plugin: habitica-sync") await this.loadSettings(); this.addSettingTab(new HabiticaSyncSettingsTab(this.app, this)); this.registerView( VIEW_TYPE, (leaf) => (new HabiticaSyncView(leaf, this)) ); - this.addRibbonIcon("popup-open", "Open Habitica Pane", () => { + this.addRibbonIcon("popup-open", "Open Habitica Pane", () => { //activate view this.activateView(); }); this.addCommand({ @@ -39,7 +32,6 @@ export default class HabiticaSync extends Plugin { this.activateView(); } }); - } async loadSettings() { this.settings = Object.assign(DEFAULT_SETTINGS, await this.loadData()) @@ -47,7 +39,6 @@ export default class HabiticaSync extends Plugin { async saveSettings() { await this.saveData(this.settings); } - async onunload() { await this.view.onClose(); @@ -57,15 +48,15 @@ export default class HabiticaSync extends Plugin { } async activateView() { this.app.workspace.detachLeavesOfType(VIEW_TYPE); - + await this.app.workspace.getRightLeaf(false).setViewState({ type: VIEW_TYPE, active: true, }); - + this.app.workspace.revealLeaf( this.app.workspace.getLeavesOfType(VIEW_TYPE)[0] ); } - + } diff --git a/src/settings.ts b/src/settings.ts index 974fe44..bd298e5 100644 --- a/src/settings.ts +++ b/src/settings.ts @@ -1,6 +1,5 @@ import HabiticaSync from "./main"; import { App, PluginSettingTab, Setting } from "obsidian"; -import moment from "moment"; export class HabiticaSyncSettingsTab extends PluginSettingTab { plugin: HabiticaSync; @@ -39,42 +38,5 @@ export class HabiticaSyncSettingsTab extends PluginSettingTab { await this.plugin.saveSettings(); }) ); - - new Setting(containerEl) - .setName("Show Task Descriptions") - .setDesc("Updates require pane re-opening") - .addToggle(cb => { - cb - .setValue(this.plugin.settings.showTaskDescription) - .onChange(async (isEnable) => { - this.plugin.settings.showTaskDescription = isEnable; - await this.plugin.saveSettings(); - }) - }); - - new Setting(containerEl) - .setName("Show Sub-Tasks") - .setDesc("Updates require pane re-opening") - .addToggle(cb => { - cb - .setValue(this.plugin.settings.showSubTasks) - .onChange(async (isEnable) => { - this.plugin.settings.showSubTasks = isEnable; - await this.plugin.saveSettings(); - }) - }); - new Setting(containerEl) - .setName("Due Date Format") - .setDesc("Update requires pane re-opening, check moment.js docs for formatting. Current Format: " + moment().format(this.plugin.settings.dueDateFormat)) - .addText((text) => - text - .setPlaceholder("DD-MM-YYYY") - .setValue(this.plugin.settings.dueDateFormat) - .onChange(async (value) => { - this.plugin.settings.dueDateFormat = value; - await this.plugin.saveSettings(); - }) - ); - } } \ No newline at end of file diff --git a/src/view.tsx b/src/view.tsx index be66720..e73dbb7 100644 --- a/src/view.tsx +++ b/src/view.tsx @@ -31,7 +31,8 @@ export class HabiticaSyncView extends ItemView { this.containerEl.children[1] ) } - async onClose(){ + + async onClose(){ ReactDOM.unmountComponentAtNode(this.containerEl.children[1]); } } \ No newline at end of file diff --git a/src/view/App.tsx b/src/view/App.tsx index 1406d23..aaf4cc0 100644 --- a/src/view/App.tsx +++ b/src/view/App.tsx @@ -1,11 +1,10 @@ import * as React from "react"; import { Notice } from "obsidian"; -import { getStats, scoreTask, makeCronReq, costReward, scoreChecklistItem } from "./habiticaAPI" +import { getStats, scoreTask, makeCronReq } from "./habiticaAPI" import Statsview from "./Components/Statsview" import Taskview from "./Components/Taskview" -import ReactDOM from "react-dom"; -class App extends React.Component { +class App extends React.Component { private _username = ""; public get username() { return this._username; @@ -34,7 +33,6 @@ class App extends React.Component { stats: { hp: 0, lvl: 0, - gold: 0, }, lastCron: "", }, @@ -45,8 +43,6 @@ class App extends React.Component { this.handleChangeTodos = this.handleChangeTodos.bind(this); this.handleChangeDailys = this.handleChangeDailys.bind(this); this.handleChangeHabits = this.handleChangeHabits.bind(this); - this.handleChangeRewards = this.handleChangeRewards.bind(this); - this.handleChangeChecklistItem = this.handleChangeChecklistItem.bind(this); this.runCron = this.runCron.bind(this); } @@ -54,10 +50,10 @@ class App extends React.Component { let cronDate = new Date(lastCron); let now = new Date(); if (cronDate.getDate() != now.getDate() || (cronDate.getMonth() != now.getMonth() || cronDate.getFullYear() != now.getFullYear())) { - return ( + return(
-
Welcome back! Please check your tasks for the last day and hit continue to get your daily rewards.
- +
Welcome back! Please check your tasks for the last day and hit continue to get your daily rewards.
+
); } @@ -77,149 +73,102 @@ class App extends React.Component { new Notice("There was an error running the cron. Please try again later."); } this.reloadData(); - } + } async reloadData() { try { - let response = await getStats(this.username, this.credentials); - let result = await response.json(); - if (result.success === false) { - new Notice('Login Failed, Please check credentials and try again!'); - } - else { - this.setState({ - isLoaded: true, - user_data: result, - tasks: result.tasks, - }); - } - } catch (e) { + let response = await getStats(this.username, this.credentials); + let result = await response.json(); + if (result.success === false) { + new Notice('Login Failed, Please check credentials and try again!'); + } + else { + this.setState({ + isLoaded: true, + user_data: result, + tasks: result.tasks, + }); + } + } catch (e) { console.log(e); new Notice("API Error: Please check credentials") - } + } } componentDidMount() { this.reloadData() } - - async sendScore(id: string, score: string, message: string) { + + async sendScore(id:string , score: string, message: string){ try { - let response = await scoreTask(this.username, this.credentials, id, score); - let result = await response.json(); - if (result.success === true) { + let response = await scoreTask(this.username, this.credentials, id, score); + let result = await response.json(); + if(result.success === true){ new Notice(message); this.reloadData(); } else { new Notice("Resyncing, please try again"); this.reloadData(); } - } catch (e) { + } catch (e) { console.log(e); new Notice("API Error: Please check credentials") - } + } } - async sendReward(id: string, score: string, message: string) { - try { - let response = await costReward(this.username, this.credentials, id, score); - let result = await response.json(); - if (result.success === true) { - new Notice(message); - this.reloadData(); - } else { - new Notice("Resyncing, please try again"); - this.reloadData(); - } - } catch (e) { - console.log(e); - new Notice("API Error: Please check credentials") - } - } - - handleChangeTodos(event: any) { + handleChangeTodos(event: any){ this.state.tasks.todos.forEach((element: any) => { - if (element.id == event.target.id) { - if (!element.completed) { - this.sendScore(event.target.id, "up", "Checked!") + if(element.id == event.target.id){ + if(!element.completed){ + this.sendScore(event.target.id,"up", "Checked!") } else { - this.sendScore(event.target.id, "down", "Un-Checked!") + this.sendScore(event.target.id,"down", "Un-Checked!") } } }) } - handleChangeDailys(event: any) { + handleChangeDailys(event: any){ this.state.tasks.dailys.forEach((element: any) => { - if (element.id == event.target.id) { - if (element.id == event.target.id) { - if (!element.completed) { - this.sendScore(event.target.id, "up", "Checked!") + if(element.id == event.target.id){ + if(element.id == event.target.id){ + if(!element.completed){ + this.sendScore(event.target.id,"up", "Checked!") } else { - this.sendScore(event.target.id, "down", "Un-Checked!") + this.sendScore(event.target.id,"down", "Un-Checked!") } } } }) } - handleChangeHabits(event: any) { + handleChangeHabits(event: any){ const target_id = event.target.id.slice(4) - if (event.target.id.slice(0, 4) == "plus") { + if(event.target.id.slice(0,4) == "plus"){ this.state.tasks.habits.forEach((element: any) => { - if (element.id == target_id) { - this.sendScore(target_id, "up", "Plus!") + if(element.id == target_id){ + this.sendScore(target_id,"up", "Plus!") } }) } else { this.state.tasks.habits.forEach((element: any) => { - if (element.id == target_id) { - this.sendScore(target_id, "down", "Minus :(") + if(element.id == target_id){ + this.sendScore(target_id,"down", "Minus :(") } }) } } - handleChangeRewards(event: any) { - const target_id = event.target.id - this.state.tasks.rewards.forEach((element: any) => { - if (element.id == event.target.id) { - if (element.id == target_id) { - this.sendReward(target_id, "down", "Redeemed!") - } - } - }) - } - async handleChangeChecklistItem(event: any){ - let parentID = event.target.parentNode.parentNode.parentNode.getAttribute("id") - let targetID = event.target.id - console.log(parentID+ " , " + targetID) - try{ - let response = await scoreChecklistItem(this.username, this.credentials, targetID, parentID); - let result = await response.json(); - if (result.success === true) { - new Notice("Checked!"); - this.reloadData(); - } else { - new Notice("Resyncing, please try again"); - this.reloadData(); - } - } catch (e) { - console.log(e); - new Notice("API Error: Please check credentials") - } - } - render() { + render(){ let content = this.CheckCron(this.state.user_data.lastCron); - if (this.state.error) - return (
Loading....
) - else if (!this.state.isLoaded) + if(this.state.error) + return(
Loading....
) + else if(!this.state.isLoaded) return
Loading....
else { return (
- {content} - - - -
+ + + {content} + ); } } diff --git a/src/view/Components/Statsview/index.tsx b/src/view/Components/Statsview/index.tsx index 506cae4..f15d886 100644 --- a/src/view/Components/Statsview/index.tsx +++ b/src/view/Components/Statsview/index.tsx @@ -3,13 +3,9 @@ import * as React from 'react'; export default function Index(props: any) { return(
- {/*
{props.user_data.profile.name}
*/} -
HP: {numberWithCommas((props.user_data.stats.hp).toFixed(0))}
-
LEVEL: {props.user_data.stats.lvl}
-
GOLD: {numberWithCommas(props.user_data.stats.gp.toFixed(2))}
+
{props.user_data.profile.name}
+
favoriteHP: {(props.user_data.stats.hp).toPrecision(3)}
+
starLVL: {props.user_data.stats.lvl}
); -} -function numberWithCommas(x: any) { - return x.toString().replace(/\B(? - -
-

-
- {/* {console.log(props.checklist)} */} - -
- + +

) } diff --git a/src/view/Components/Taskview/Dailiesview/DailySubTasks.tsx b/src/view/Components/Taskview/Dailiesview/DailySubTasks.tsx deleted file mode 100644 index 09e4c99..0000000 --- a/src/view/Components/Taskview/Dailiesview/DailySubTasks.tsx +++ /dev/null @@ -1,22 +0,0 @@ -import * as React from "react"; -import renderMarkdown from "../markdownRender"; - -function DailySubTasks(props: any) { - - if (props.subtasks) { - const subtasks = props.subtasks.map((subtask: any) => { - let subtask_text = renderMarkdown(subtask.text); - return ( -
- -

-
- ) - }); - return subtasks - } - else { - return
- } -} -export default DailySubTasks \ No newline at end of file diff --git a/src/view/Components/Taskview/Dailiesview/index.tsx b/src/view/Components/Taskview/Dailiesview/index.tsx index db5944b..0d0f192 100644 --- a/src/view/Components/Taskview/Dailiesview/index.tsx +++ b/src/view/Components/Taskview/Dailiesview/index.tsx @@ -3,89 +3,23 @@ import DailyItem from "./DailyItem" import { Tab, Tabs, TabList, TabPanel } from "react-tabs"; export default function Index(props: any){ - if(props.dailys == undefined) { return
No Dailies Present
} else { - - const notDueDailies = props.dailys.map((daily: any) => { - - if (!daily.isDue) { - let daily_notes = ''; - let daily_subtasks = ''; - if (props.settings.showTaskDescription) { - daily_notes = daily.notes; - } - - if (props.settings.showSubTasks) { - daily_subtasks = daily.checklist; - } - return - } - }) - const incompleteDailies = props.dailys.map((daily: any) => { - if (!daily.completed&&daily.isDue) { - let daily_notes = ''; - let daily_subtasks = ''; - if (props.settings.showTaskDescription) { - daily_notes = daily.notes; - } - - if (props.settings.showSubTasks) { - daily_subtasks = daily.checklist; - } - return - } - }) + if(!daily.completed) + return + }) const completedDailies = props.dailys.map((daily: any) => { - // if(daily.completed) - // return - if (daily.completed) { - let daily_notes = ''; - let daily_subtasks = ''; - if (props.settings.showTaskDescription) { - daily_notes = daily.notes; - } - - if (props.settings.showSubTasks) { - daily_subtasks = daily.checklist; - } - return - } + if(daily.completed) + return }) - - const allDailies = props.dailys.map((daily: any) => { - // if(daily.completed) - // return - let daily_notes = ''; - let daily_subtasks = ''; - if (props.settings.showTaskDescription) { - daily_notes = daily.notes; - } - - if (props.settings.showSubTasks) { - daily_subtasks = daily.checklist; - } - return - }) - const display =
Active Completed - Not Due - All
    {incompleteDailies}
@@ -93,15 +27,10 @@ export default function Index(props: any){
    {completedDailies}
- -
    {notDueDailies}
-
- -
    {allDailies}
-
return(display); } } + diff --git a/src/view/Components/Taskview/Habitsview/HabitItem.tsx b/src/view/Components/Taskview/Habitsview/HabitItem.tsx index 37d672c..fa397cc 100644 --- a/src/view/Components/Taskview/Habitsview/HabitItem.tsx +++ b/src/view/Components/Taskview/Habitsview/HabitItem.tsx @@ -1,23 +1,16 @@ +import Emoji from "react-emoji-render"; import * as React from "react"; -import renderMarkdown from "../markdownRender"; function HabitItem(props: any) { - let habit_text = renderMarkdown(props.habit_text); - let habit_notes = renderMarkdown(props.habit_notes); return (
-
- - -
-
-

-
-
+ +

+
) } diff --git a/src/view/Components/Taskview/Habitsview/index.tsx b/src/view/Components/Taskview/Habitsview/index.tsx index 1d0107c..dc322bb 100644 --- a/src/view/Components/Taskview/Habitsview/index.tsx +++ b/src/view/Components/Taskview/Habitsview/index.tsx @@ -9,11 +9,7 @@ export default function Index(props: any){ } else { const allHabits = props.habits.map((habit: any) => { - if (props.settings.showTaskDescription) { - return - } else { - return - } + return }) const display =
    {allHabits}
diff --git a/src/view/Components/Taskview/Rewardview/RewardItem.tsx b/src/view/Components/Taskview/Rewardview/RewardItem.tsx deleted file mode 100644 index 5f331e2..0000000 --- a/src/view/Components/Taskview/Rewardview/RewardItem.tsx +++ /dev/null @@ -1,21 +0,0 @@ -import * as React from "react"; -import renderMarkdown from "../markdownRender"; - -function RewardItem(props: any) { - let reward_text = renderMarkdown(props.reward_text); - let reward_notes = renderMarkdown(props.reward_notes); - return ( -
-
- -
-
-

-
-
- -
- ) -} - -export default RewardItem \ No newline at end of file diff --git a/src/view/Components/Taskview/Rewardview/index.tsx b/src/view/Components/Taskview/Rewardview/index.tsx deleted file mode 100644 index 4ddc21a..0000000 --- a/src/view/Components/Taskview/Rewardview/index.tsx +++ /dev/null @@ -1,25 +0,0 @@ -import * as React from "react"; -import RewardItem from "./RewardItem" - -export default function Index(props: any){ - if(props.rewards == undefined) { - return (
- No Rewards present. -
) - } - else { - const allRewards = props.rewards.map((reward: any) => { - if (props.settings.showTaskDescription) { - return - } else { - return - } - }) - const display =
-
    {allRewards}
-
- - return(display); - } -} - diff --git a/src/view/Components/Taskview/TodoItem.tsx b/src/view/Components/Taskview/TodoItem.tsx new file mode 100644 index 0000000..c02e230 --- /dev/null +++ b/src/view/Components/Taskview/TodoItem.tsx @@ -0,0 +1,13 @@ +import { Emoji } from 'react-emoji-render'; +import * as React from "react"; + +function TodoItem(props: any) { + return ( +
+ + +
+ ) +} + +export default TodoItem \ No newline at end of file diff --git a/src/view/Components/Taskview/Todoview/TodoItem.tsx b/src/view/Components/Taskview/Todoview/TodoItem.tsx index 7c1653b..2766dbe 100644 --- a/src/view/Components/Taskview/Todoview/TodoItem.tsx +++ b/src/view/Components/Taskview/Todoview/TodoItem.tsx @@ -1,21 +1,11 @@ +import Emoji from "react-emoji-render"; import * as React from "react"; -import TodoSubTasks from "./TodoSubTasks"; -import renderMarkdown from "../markdownRender" -import moment from "moment"; function TodoItem(props: any) { - var dueDate = (props.dueDate==null)?"":("Due Date:"+(moment(props.dueDate).format(props.dueDateFormat))); - var text_html = renderMarkdown(props.todo_text); - var note_html = renderMarkdown(props.todo_notes); return (
-
-

-
- -
{dueDate}
-
+

) } diff --git a/src/view/Components/Taskview/Todoview/TodoSubTasks.tsx b/src/view/Components/Taskview/Todoview/TodoSubTasks.tsx deleted file mode 100644 index 92ab97a..0000000 --- a/src/view/Components/Taskview/Todoview/TodoSubTasks.tsx +++ /dev/null @@ -1,21 +0,0 @@ -import * as React from "react"; -import renderMarkdown from "../markdownRender"; - -function TodoSubTasks(props: any) { - if (props.subtasks) { - const subtasks = props.subtasks.map((subtask: any) => { - let subtask_text = renderMarkdown(subtask.text); - return ( -
- -

-
- ) - }); - return subtasks - } - else { - return
- } -} -export default TodoSubTasks \ No newline at end of file diff --git a/src/view/Components/Taskview/Todoview/index.tsx b/src/view/Components/Taskview/Todoview/index.tsx index 035b52e..7ce2edf 100644 --- a/src/view/Components/Taskview/Todoview/index.tsx +++ b/src/view/Components/Taskview/Todoview/index.tsx @@ -8,26 +8,12 @@ export default function Index(props: any){ } else { const incompleteTodos = props.todos.map((todo: any) => { - - if(!todo.completed) { - let todo_notes = ''; - let todo_subtasks = ''; - if (props.settings.showTaskDescription) { - todo_notes = todo.notes; - } - - if (props.settings.showSubTasks) { - todo_subtasks = todo.checklist; - } - return - } - + if(!todo.completed) + return }) const completedTodos = props.todos.map((todo: any) => { if(todo.completed) - return + return }) const display =
@@ -36,10 +22,10 @@ export default function Index(props: any){ Completed -
    {incompleteTodos}
+
    {incompleteTodos}
-
    {completedTodos}
+
    {completedTodos}
diff --git a/src/view/Components/Taskview/Todoview/tabs.ts b/src/view/Components/Taskview/Todoview/tabs.ts new file mode 100644 index 0000000..55153e7 --- /dev/null +++ b/src/view/Components/Taskview/Todoview/tabs.ts @@ -0,0 +1 @@ +import * as React from "react" diff --git a/src/view/Components/Taskview/index.tsx b/src/view/Components/Taskview/index.tsx index 06d2874..9546979 100644 --- a/src/view/Components/Taskview/index.tsx +++ b/src/view/Components/Taskview/index.tsx @@ -2,41 +2,33 @@ import * as React from "react"; import Dailiesview from "./Dailiesview" import Habitsview from "./Habitsview" import Todoview from "./Todoview" -import Rewardview from "./Rewardview" import { Tab, Tabs, TabList, TabPanel } from "react-tabs"; export default function Index(props: any){ const display =
- + + task_alt + today - - add_chart - - assignment_turned_in - - - account_balance + add_circle_outline - + - + - - - - +
return(display); -} +} //yes diff --git a/src/view/Components/Taskview/markdownRender.ts b/src/view/Components/Taskview/markdownRender.ts deleted file mode 100644 index e09aa1f..0000000 --- a/src/view/Components/Taskview/markdownRender.ts +++ /dev/null @@ -1,21 +0,0 @@ -import MarkdownIt from "markdown-it"; -import markdownitEmoji from "markdown-it-emoji" -import twemoji from "twemoji"; - -export default function renderMarkdown(markdown: string) { - //check if markdown is empty or not a string - if (markdown === "" || markdown === undefined) { - return ""; - } - const md = new MarkdownIt({ - html: true, - breaks: true, - linkify: true, - typographer: true - }); - md.use(markdownitEmoji); - md.renderer.rules.emoji = function(token, idx) { - return twemoji.parse(token[idx].content); - }; - return md.render(markdown); -} \ No newline at end of file diff --git a/src/view/habiticaAPI.ts b/src/view/habiticaAPI.ts index eae3ab8..142a923 100644 --- a/src/view/habiticaAPI.ts +++ b/src/view/habiticaAPI.ts @@ -39,32 +39,4 @@ export async function makeCronReq(username: string, credentials: string){ } }) return(response) -} - -export async function costReward(username: string, credentials: string, taskID: string, direction: string) { - const url = "https://habitica.com/api/v4/tasks/".concat(taskID).concat("/score/").concat(direction) - const response = fetch(url, { - method: 'POST', - headers: { - "Content-Type": "application/json", - "x-client": "278e719e-5f9c-43b1-9dba-8b73343dc062-HabiticaSync", - "x-api-user": username, - "x-api-key": credentials, - } - }) - return(response) -} - -export async function scoreChecklistItem(username: string, credentials: string, checklistItemID: string, taskID: string) { - const url = "https://habitica.com/api/v3/tasks/".concat(taskID).concat("/checklist/").concat(checklistItemID).concat("/score") - const response = fetch(url, { - method: 'POST', - headers: { - "Content-Type": "application/json", - "x-client": "278e719e-5f9c-43b1-9dba-8b73343dc062-HabiticaSync", - "x-api-user": username, - "x-api-key": credentials, - } - }) - return(response) } \ No newline at end of file diff --git a/styles.css b/styles.css index 90c9ec1..b31b4a2 100644 --- a/styles.css +++ b/styles.css @@ -1,9 +1,3 @@ -@import url('https://fonts.googleapis.com/css2?family=Open+Sans:ital,wght@1,300&display=swap'); -@import url('https://fonts.googleapis.com/css2?family=Open Sans:ital,wght@0,400;1,100&family=Roboto&display=swap'); - -.add-task-input { - display: flex; -} #profile-name { font-size: x-large; @@ -11,149 +5,79 @@ padding-bottom: 3%; } .stats { - width: 95%; - display: flex; - justify-content: space-between; - font-weight: bold; - padding-bottom: 5px; -} - -.stats-view { - border-bottom: 1px; -} -.modify-todo { - align-self: center; -} - -.delete-todo { - align-self: center; + padding-bottom: 6px; } .todo-item { - display: grid; - grid-template-columns: 1fr 30fr 1fr 1fr; - justify-content: left; - align-items: flex-start; - padding-top: 5px; - padding-bottom: 5px; - width: 100%; - border-bottom: 1px solid #cecece; - font-family: Roboto, sans-serif; - font-weight: bold; - font-size: 16px; - padding-left: 0; -} - -.description { - font-family: Open Sans, sans-serif; - font-weight: 100; -} -.description > ul { - list-style-type: none; -} -p { - margin: 0; + display: flex; + justify-content: flex-start; + align-items: center; + padding: 0px 0px 0; + width: 80%; + border-bottom: 1px solid #cecece; + font-family: Roboto, sans-serif; + font-weight: normal; + font-size: 16px; } .habit-text { - text-align: left !important; - font-weight: bold; - padding-top: 5px; - width: 80%; + text-align: center !important; + padding: 0px; + width: 50%; margin-right: 20px; } -.habit-button { - background-color: var(--interactive-accent); +.habit-plus { + /* background-color: #fff; */ border: none; - /* color: black; */ + color: white; + padding: 7px 10px; text-align: center; text-decoration: none; font-size: 16px; - display: block; - width: 100%; - color: var(--text-on-accent); } -/* habit-button on hover css selector */ -.habit-button:hover { - color: var(--text-on-accent); - background-color: var(--interactive-accent-hover); + +.habit-minus { + /* background-color: #fff; */ + /* border-radius: 50%; */ + border: none; + color: white; + padding: 7px 10px; + text-align: center; + text-decoration: none; + font-size: 16px; } .habit-item { display: flex; - grid-template-columns: 60px 1fr; + /* justify-content: center; */ + align-content: space-between; + align-items: center; + padding: 0px 0px 0; width: 100%; - gap: 5px; border-bottom: 1px solid #cecece; - font-family: Open Sans, sans-serif; - font-weight: 100%; + font-family: Roboto, sans-serif; + font-weight: 50%; font-size: 16px; - padding-top: 5px; - padding-bottom: 5px; -} - -.habit-button-grp { - display: flex; - flex-direction: column; - justify-content: flex-start; - align-content: stretch; - height: 100%; + } input[type=checkbox] { margin-right: 10px; - margin-top: 5px; - align-self: start; -} - -.todo-content { - align-self: center; -} - -.submit-button { - /* padding: 5px 5px; */ - font-size: 15px; - border: 1px solid #aaa; - /* white-space: nowrap; */ - /* margin: 10px; */ - margin: 0; } input[type=checkbox]:focus { outline: 0; } -::-webkit-scrollbar { - display: none; /* Chrome Safari */ -} - .plugin-root { min-width: 260px; - display: flex; - flex-direction: column; - justify-content: flex-start; - align-items: stretch; -} - -#classDisplay { - height: 100%; - width: 100%; -} - - -.view-content { - margin-bottom: 0; } .substats { font-size: medium; } -ul { - margin: 0; -} - /* react-tabs internal file :wink: */ .material-icons { font-size: 12px !important; @@ -170,12 +94,12 @@ ul { .react-tabs { -webkit-tap-highlight-color: transparent; - height: 100%; + } .react-tabs__tab-list { border-bottom: 1px solid #aaa; - margin: 0 0 5px; + margin: 0 0 10px; padding: 0; } @@ -220,14 +144,6 @@ ul { .react-tabs__tab-panel { display: none; - left: 0px; - height: 88%; - /* overflow: scroll; */ -} - -.task-panel { - overflow: scroll; - height: 100%; } .react-tabs__tab-panel--selected { @@ -243,45 +159,9 @@ ul li:not(.task-list-item)::before { font-weight: bold; text-shadow: 0 0 0.5em transparent; } - -.task-operation { - align-self: center; - margin: 0; - padding: 0; -} - -.edit-item { - display: flex; - flex-direction: column; - width: 100%; -} - -.edit-button { - display: flex; - flex-direction: row; - justify-content: flex-end; -} - -.task-submit { - display: grid; - grid-template-columns: 10fr 5fr; -} - -.add-task-input { - display: block; - width: 100%; -} - -.task-input-box { - margin-right: 10px; -} - -button { +body > div.app-container.is-left-sidedock-collapsed.is-right-sidedock-collapsed > div.horizontal-main-container > div > div.workspace-split.mod-horizontal.mod-right-split > div.workspace-tabs > div.workspace-leaf > div > div.view-content > div > div.cron > button { margin: auto; margin-bottom: 5px; - white-space: nowrap; - padding: 5px 5px; - margin-right: 0; } .cron { display: inline-grid; @@ -291,6 +171,7 @@ button { margin-left: 10%; margin-right: 10%; margin-bottom: 10px; + background-color: var(--background-secondary-alt); border-radius: 10px; } #cronMessage { @@ -298,26 +179,3 @@ button { margin-bottom: 10px; color: var(--text-normal) } -#cronButton { - margin: auto; - margin-bottom: 5px; - white-space: nowrap; - padding: 5px 5px; - background-color: var(--interactive-accent); - margin-right: auto; -} - -.subtask { - display: flex; - flex-direction: row; - font-weight: normal; - font-family: Roboto, sans-serif; - justify-content: flex-start; -} -.emoji { - height: 1em; -} -.description>ul { - list-style-type: disc; - margin-left: 10% !important; -} diff --git a/tsconfig.json b/tsconfig.json index c6bbfcb..48f3cf9 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -9,8 +9,6 @@ "noImplicitAny": true, "moduleResolution": "node", "importHelpers": true, - "allowSyntheticDefaultImports": true, - "esModuleInterop": true, "lib": [ "dom", "es5",