1
0
forked from mirror/misskey
This commit is contained in:
syuilo 2018-02-23 02:06:35 +09:00
parent e0ffedca24
commit c686a10472
7 changed files with 127 additions and 34 deletions

View File

@ -194,6 +194,11 @@ const endpoints: Endpoint[] = [
withCredential: true, withCredential: true,
secure: true secure: true
}, },
{
name: 'i/update_client_setting',
withCredential: true,
secure: true
},
{ {
name: 'i/pin', name: 'i/pin',
kind: 'account-write' kind: 'account-write'

View File

@ -46,19 +46,13 @@ module.exports = async (params, user, _, isSecure) => new Promise(async (res, re
if (bannerIdErr) return rej('invalid banner_id param'); if (bannerIdErr) return rej('invalid banner_id param');
if (bannerId) user.banner_id = bannerId; if (bannerId) user.banner_id = bannerId;
// Get 'show_donation' parameter
const [showDonation, showDonationErr] = $(params.show_donation).optional.boolean().$;
if (showDonationErr) return rej('invalid show_donation param');
if (showDonation) user.client_settings.show_donation = showDonation;
await User.update(user._id, { await User.update(user._id, {
$set: { $set: {
name: user.name, name: user.name,
description: user.description, description: user.description,
avatar_id: user.avatar_id, avatar_id: user.avatar_id,
banner_id: user.banner_id, banner_id: user.banner_id,
profile: user.profile, profile: user.profile
'client_settings.show_donation': user.client_settings.show_donation
} }
}); });

View File

@ -0,0 +1,43 @@
/**
* Module dependencies
*/
import $ from 'cafy';
import User, { pack } from '../../models/user';
import event from '../../event';
/**
* Update myself
*
* @param {any} params
* @param {any} user
* @return {Promise<any>}
*/
module.exports = async (params, user) => new Promise(async (res, rej) => {
// Get 'name' parameter
const [name, nameErr] = $(params.name).string().$;
if (nameErr) return rej('invalid name param');
// Get 'value' parameter
const [value, valueErr] = $(params.value).nullable.any().$;
if (valueErr) return rej('invalid value param');
const x = {};
x[`client_settings.${name}`] = value;
await User.update(user._id, {
$set: x
});
// Serialize
user.client_settings[name] = value;
const iObj = await pack(user, user, {
detail: true,
includeSecrets: true
});
// Send response
res(iObj);
// Publish i updated event
event(user._id, 'i_updated', iObj);
});

View File

@ -33,7 +33,11 @@ export default Vue.component('mk-post-html', {
.replace(/(\r\n|\n|\r)/g, '\n'); .replace(/(\r\n|\n|\r)/g, '\n');
if ((this as any).shouldBreak) { if ((this as any).shouldBreak) {
return text.split('\n').map(t => [createElement('span', t), createElement('br')]); if (text.indexOf('\n') != -1) {
return text.split('\n').map(t => [createElement('span', t), createElement('br')]);
} else {
return createElement('span', text);
}
} else { } else {
return createElement('span', text.replace(/\n/g, ' ')); return createElement('span', text.replace(/\n/g, ' '));
} }

View File

@ -1,7 +1,7 @@
<template> <template>
<div class="mk-home" :data-customize="customize"> <div class="mk-home" :data-customize="customize">
<div class="customize" v-if="customize"> <div class="customize" v-if="customize">
<a href="/">%fa:check%完了</a> <router-link to="/">%fa:check%完了</router-link>
<div> <div>
<div class="adder"> <div class="adder">
<p>ウィジェットを追加:</p> <p>ウィジェットを追加:</p>
@ -51,7 +51,11 @@
</div> </div>
</x-draggable> </x-draggable>
<div class="main"> <div class="main">
<mk-timeline ref="tl" @loaded="onTlLoaded"/> <a @click="hint">カスタマイズのヒント</a>
<div>
<mk-post-form v-if="os.i.client_settings.showPostFormOnTopOfTl"/>
<mk-timeline ref="tl" @loaded="onTlLoaded"/>
</div>
</div> </div>
</template> </template>
<template v-else> <template v-else>
@ -59,6 +63,7 @@
<component v-for="widget in widgets[place]" :is="`mkw-${widget.name}`" :key="widget.id" :widget="widget" @chosen="warp"/> <component v-for="widget in widgets[place]" :is="`mkw-${widget.name}`" :key="widget.id" :widget="widget" @chosen="warp"/>
</div> </div>
<div class="main"> <div class="main">
<mk-post-form v-if="os.i.client_settings.showPostFormOnTopOfTl"/>
<mk-timeline ref="tl" @loaded="onTlLoaded" v-if="mode == 'timeline'"/> <mk-timeline ref="tl" @loaded="onTlLoaded" v-if="mode == 'timeline'"/>
<mk-mentions @loaded="onTlLoaded" v-if="mode == 'mentions'"/> <mk-mentions @loaded="onTlLoaded" v-if="mode == 'mentions'"/>
</div> </div>
@ -126,23 +131,19 @@ export default Vue.extend({
deep: true deep: true
}); });
}, },
mounted() {
this.$nextTick(() => {
if (this.customize) {
(this as any).apis.dialog({
title: '%fa:info-circle%カスタマイズのヒント',
text: '<p>ホームのカスタマイズでは、ウィジェットを追加/削除したり、ドラッグ&ドロップして並べ替えたりすることができます。</p>' +
'<p>一部のウィジェットは、<strong><strong>右</strong>クリック</strong>することで表示を変更することができます。</p>' +
'<p>ウィジェットを削除するには、ヘッダーの<strong>「ゴミ箱」</strong>と書かれたエリアにウィジェットをドラッグ&ドロップします。</p>' +
'<p>カスタマイズを終了するには、右上の「完了」をクリックします。</p>',
actions: [{
text: 'Got it!'
}]
});
}
});
},
methods: { methods: {
hint() {
(this as any).apis.dialog({
title: '%fa:info-circle%カスタマイズのヒント',
text: '<p>ホームのカスタマイズでは、ウィジェットを追加/削除したり、ドラッグ&ドロップして並べ替えたりすることができます。</p>' +
'<p>一部のウィジェットは、<strong><strong>右</strong>クリック</strong>することで表示を変更することができます。</p>' +
'<p>ウィジェットを削除するには、ヘッダーの<strong>「ゴミ箱」</strong>と書かれたエリアにウィジェットをドラッグ&ドロップします。</p>' +
'<p>カスタマイズを終了するには、右上の「完了」をクリックします。</p>',
actions: [{
text: 'Got it!'
}]
});
},
onTlLoaded() { onTlLoaded() {
this.$emit('loaded'); this.$emit('loaded');
}, },
@ -193,10 +194,16 @@ export default Vue.extend({
background-image url('/assets/desktop/grid.svg') background-image url('/assets/desktop/grid.svg')
> .main > .main > .main > .main
cursor not-allowed !important > a
display block
margin-bottom 8px
text-align center
> * > div
pointer-events none cursor not-allowed !important
> *
pointer-events none
&:not([data-customize]) &:not([data-customize])
> .main > *:empty > .main > *:empty
@ -287,6 +294,11 @@ export default Vue.extend({
width calc(100% - 275px * 2) width calc(100% - 275px * 2)
order 2 order 2
.mk-post-form
margin-bottom 16px
border solid 1px #e5e5e5
border-radius 4px
> *:not(.main) > *:not(.main)
width 275px width 275px
padding 16px 0 16px 0 padding 16px 0 16px 0

View File

@ -1,13 +1,19 @@
<template> <template>
<mk-window is-modal width='700px' height='550px' @closed="$destroy"> <mk-window ref="window" is-modal width="700px" height="550px" @closed="$destroy">
<span slot="header" :class="$style.header">%fa:cog%設定</span> <span slot="header" :class="$style.header">%fa:cog%設定</span>
<mk-settings/> <mk-settings @done="close"/>
</mk-window> </mk-window>
</template> </template>
<script lang="ts"> <script lang="ts">
import Vue from 'vue'; import Vue from 'vue';
export default Vue.extend({}); export default Vue.extend({
methods: {
close() {
(this as any).$refs.window.close();
}
}
});
</script> </script>
<style lang="stylus" module> <style lang="stylus" module>

View File

@ -20,7 +20,13 @@
<section class="web" v-show="page == 'web'"> <section class="web" v-show="page == 'web'">
<h1>デザイン</h1> <h1>デザイン</h1>
<a href="/i/customize-home" class="ui button">ホームをカスタマイズ</a> <div>
<button class="ui button" @click="customizeHome">ホームをカスタマイズ</button>
</div>
<label>
<input type="checkbox" v-model="showPostFormOnTopOfTl" @change="onChangeShowPostFormOnTopOfTl">
<span>タイムライン上部に投稿フォームを表示する</span>
</label>
</section> </section>
<section class="drive" v-show="page == 'drive'"> <section class="drive" v-show="page == 'drive'">
@ -89,8 +95,25 @@ export default Vue.extend({
}, },
data() { data() {
return { return {
page: 'profile' page: 'profile',
showPostFormOnTopOfTl: false
}; };
},
created() {
this.showPostFormOnTopOfTl = (this as any).os.i.client_settings.showPostFormOnTopOfTl;
},
methods: {
customizeHome() {
this.$router.push('/i/customize-home');
this.$emit('done');
},
onChangeShowPostFormOnTopOfTl() {
(this as any).api('i/update_client_setting', {
name: 'showPostFormOnTopOfTl',
value: this.showPostFormOnTopOfTl
});
}
} }
}); });
</script> </script>
@ -146,4 +169,10 @@ export default Vue.extend({
color #555 color #555
border-bottom solid 1px #eee border-bottom solid 1px #eee
> .web
> div
border-bottom solid 1px #eee
padding 0 0 16px 0
margin 0 0 16px 0
</style> </style>