how to change confige react-mui-draft-wysiwyg? - javascript

I use HTML editor material ui :
import MUIEditor, { MUIEditorState } from "react-mui-draft-wysiwyg";
<MUIEditor
editorState={formElement.editorState}
onChange={formElement.onChange}
/>
I want to remove the font color button in the toolbar. When I go to the MUIEditor file at node-modules and I want to make some changes to that file but it does not seem to change even when I get a console I can not see the result. What should I do?
.node_modules
.react-mui-draft-wysiwyg
.dist
.index.js

It is rarely advisable to edit the contents of /node_modules -- instead react-mui-draft-wysiwyg provides direct a way to customize the toolbar configuration through the config prop, in your own React code.
In your case, to hide the font color button, you simply need to pass in the menu options that you would like to display. (ie. remove/comment out the toolbarControlTypes.fontColor option). For example:
import MUIEditor, {
MUIEditorState,
toolbarControlTypes // Added toolbarControlTypes
} from "react-mui-draft-wysiwyg";
...
<MUIEditor
editorState={editorState}
onChange={onChange}
config={{
toolbar: {
controls: [
toolbarControlTypes.undo,
toolbarControlTypes.redo,
toolbarControlTypes.divider,
toolbarControlTypes.bold,
toolbarControlTypes.italic,
toolbarControlTypes.underline,
toolbarControlTypes.strikethrough,
// Include all of the default toolbar options except for fontColor
// toolbarControlTypes.fontColor,
toolbarControlTypes.fontBackgroundColor,
toolbarControlTypes.divider,
toolbarControlTypes.linkAdd,
toolbarControlTypes.linkRemove,
toolbarControlTypes.image,
toolbarControlTypes.divider,
toolbarControlTypes.blockType,
toolbarControlTypes.fontSize,
toolbarControlTypes.fontFamily,
toolbarControlTypes.textAlign,
toolbarControlTypes.divider,
toolbarControlTypes.unorderedList,
toolbarControlTypes.orderedList
]
}
}}
/>
Documentation: Default Configuration Options
Working CodeSandbox: https://codesandbox.io/s/mui4-draft-wysiwyg-bre8e?file=/demo.js

Related

Is there a way to add a personal icon on Select ( Mantine)- not an image from Tabler Icons

I am new on Mantine and I`m trying to do a Search Component. In stead of using an image from tabler icons as is present in the mantine examples, I want to add a picture from my assets.
This is what I`ve tried
import { ReactComponent as SearchIcon } from '../../assets/search.svg';
import { IconHash } from '#tabler/icons';
<Select
className={classes.searchBar}
radius="xl"
placeholder="Cauta produse, servicii, sau parteneri"
itemComponent={SelectItem}
data={data}
searchable
icon={<SearchIcon />}
maxDropdownHeight={400}
nothingFound="Nobody here"
filter={(value, item) =>
item.label.toLowerCase().includes(value.toLowerCase().trim()) ||
item.description.toLowerCase().includes(value.toLowerCase().trim())
}
/>
looks like if I import Icon Hash, the type is a function
Of course you can. icon is of type ReactNode and thus accepts every react node you pass to it. You should make sure that your svg is a react component, though.
The return type from #tabler\icons is indeed a function (actually, a component) because they're meant to be used as react components. You can check an example here and configure your svg accordingly: https://github.com/tabler/tabler-icons/blob/master/icons-react/icons-js/123.js.

Can I hide commas from a JSX bug using custom CSS?

One component of my website is based on the following .js code:
items.add(
`field-${field.id()}`,
<div className="Mason-Field Form-group">
<label>
{field.icon() ? <>{icon(field.icon())} </> : null}
{field.name()}
</label>
,<div className="FormControl Mason-Inline-Answers">{answer_list}</div>,
</div>
);
In the website, the commas are literally in the JSX just like they appear in the output. This must be an oversight when the hyperscript was converted to JSX. See the following test post screenshot.
I personally am not able to fix this in the .js level. Is there a way to hide the commas in the CSS level?
Test pose
The approach is to set the font color of the outer div to transparent and then set it again on the children:
.Mason-Field.Form-group { color: transparent }
.Mason-Field.Form-group > * { color: initial }
Depending on your other classes FormControl and Mason-Inline-Answers, you might need to be more specific.

Dynamically importing css files into react

i am wondering is there a way to dynamically import a css file into react.
say i have a css file named style-light.css and i have another named style-dark.css.
is there a way to use react state or some other method to dynamically import the css files into the component based on the current value of the state ?
eg
import "../style-light.css" // default import
export default function TestImport(){
const [switch, setSwitch] = useState("light");
if(switch === "dark"){
import "../style-dark.css" // adds the style-dark import below the light one to overwrite the light css.
}
return (
<div>
<button onClick={()=> setSwitch("dark")}> click to get dark css </button>
</div>
)
}
bascially something like that?
any insight will be helpful. thanks
Option 1
For that I would recommend that you use CSS variables and only one CSS file. You can change the values of your variables based on a class applied on your page body. For example:
variables.css
:root {
--textColor: black;
}
[class="dark-theme"] {
--textColor: white;
}
With javascript you can add or remove the class from your html document, like this
component.js
document.documentElement.classList.add('dark-theme')
document.documentElement.classList.remove('dark-theme')
On your components styles you can use the variables with var(--variable)
component.css
.my-component-class {
color: var(--textColor);
}
Option 2
Use some CSS-IN-JS library like styled-components or emotion, you can use a ThemeProvider to change our theme accordingly with some state in your application. See this example here: https://styled-components.com/docs/advanced#theming

How to avoid Vuetify overrides default CSS

Summarize the problem
I am trying to implement the Vuetify to a part of an existing project. But after I added Vuetify to the Project. I found out that the "default" CSS styles for like input field, select are changed. And it makes those input field and select all look like plain text rather than input field and select.
Because I only want to implement the Vuetify for a part of the project, so it is bad that the Vuetify overrides the "default" CSS Rules.
I am looking for a way to implement the Vuetify for a part of an existing project. But the rest of the project should be rendered as normal (just with default CSS, not my own CSS).
To make the Qustion more clair, I will put an example which shows two selects. The first one is made with Vuetify <v-select> and the second one is made with normal HTML code <select>
Provide background and tell us what you've already tried
I have already tried to put custom CSS rules for input field and select after the Vuetify Script and Vuetify CSS link. But Vuetify still overrides my custom CSS-Styles.
Show your code
HTML PART:
<div id="app">
<div>Vuetify select:</div>
<v-select
:items="items"
>
</v-select>
<hr/>
<div>
<div>Normal select:</div>
<select>
<option value="0">test1</option>
<option value="1">test2</option>
<option value="2">test3</option>
</select>
</div>
</div>
JS PART:
new Vue({
el: '#app',
data() {
return {
item: null,
items: [
{
text: "a"
},
{
text: "b"
},
{
text: "c"
},
]
}
}
})
Describe expected and actual results
I expected that I can use Vuetify for some parts of this project. But in the meanwhile, the rest of the project should be acting just like normal (with default CSS).
This is caused by the Vuetify reset styles (src/styles/generic/_reset.scss).
There is also an issue for that problem: https://github.com/vuetifyjs/vuetify/issues/8530. You can find there a little postcss hack from mkalus that isolates necessary styles via the wrapper (adding the prefix class to selectors).
In my case I just needed to remove some element selectors, excluding those that I added myself. So this is my variation of mkalus's solution with the postcss-filter-rules plugin.
I used the filter option to filter selectors. Its description:
Selectors are kept if the function returns true, otherwise they are removed.
And the keepAtRules option to prevent unnecessary deletions:
By default, #font-face and any empty at-rules (after filtering) are removed. To keep specific at-rules, provide an array of names to this option. To keep all at-rules, use the value true.
vue.config.js (Vue CLI 4):
const autoprefixer = require('autoprefixer')
const filterRules = require('postcss-filter-rules')
module.exports = {
/* ... */
css: {
loaderOptions: {
postcss: {
plugins: [
filterRules({
filter: (selector) => {
const re = new RegExp(/^(html|body|\*|ul|ol|select|small)(\W|$)/, 'i')
const exception = '.vue-global'
return !re.test(selector) || selector.includes(exception)
},
keepAtRules: true
}),
autoprefixer
]
}
}
}
/* ... */
}
Now that I've removed some Vuetify reset styles, I can still style html and other elements like this:
html.vue-global
font-size 16px
You can try adding a normalize css file to your project and the vuetify styling should only apply to when you want it to, i use this

Multiple TinyMCE editors, but only one toolbar?

I've looked around the forum, but cannot seem to find a definite answer to this problem...
I'm using jQuery and TinyMCE on our website. I've gone through the docs of TinyMCE, but am still getting lost I'm afraid. We're doing an interface that requires edit-in-place in multiple places in the page. The only thing is, each of these will have all the editing choices from TinyMCE in one toolbar at the top. So, to recap it, it's multiple editors (that each have no toolbars of their own, just a place to edit or select the text) and only one toolbar at the top of the page to control whichever textbox is active at the time.
How could this be achieved? Is it even possible? Any help, any push in the right direction, any hints/tips/knowledge at all on this problem would be a great, great help.
Thanks, James
I did with the 3.x version like this (it's Prototype syntax):
First, I created a toolbar wrapper (in my case I attached it with position:fixed at top of the document:
<div id="externalToolbarWrapper"></div>
Then I set the setup function in the tinyMCE-settings (for each editor) like this:
[...]
theme_advanced_toolbar_location : "external",
setup : function(ed) {
ed.onInit.add(function(ed, e) {
ed.onPostRender.add(function(ed, cm) {
var toolbar = $(ed.id + '_external');
// inserts the external toolbar in the external wrapper
$('externalToolbarWrapper').insert(toolbar.hide());
});
ed.onRemove.add(function(ed) {
if($(ed.id + '_external')) {
// removes external toolbar
$(ed.id + '_external').remove();
}
});
});
}
This worked in my case - the editors show/hide the toolbars on activation/deactivation.
I know there is a way to show the toolbar when a textarea is focused into, and then hide on textarea blur event - so that could be one route.
I do a similar sort of thing (with multiple textareas) where i load in demand the tinyMCE, so something like loading on demand and then destroy when finished with (blur event) might be what you're after.
I can't give you all of my code as it's actually part of my employer's I.P, but here is a rough outline to it, hopefully should help. The tinyMCE_GZ is part of the gzip which is off the tinyMCE site.
isTinyMCE_Loaded = false;
jQuery('.my-textarea').one("click", function(){
BuildWYSIWYG.Full(jQuery(this));
})
BuildWYSIWYG.OnDemand: function(callback){
tinyMCE_GZ.init({
plugins : 'style,table,advhr,advimage,advlink,insertdatetime,preview,searchreplace,contextmenu,paste,fullscreen,visualchars,nonbreaking,xhtmlxtras,safari,tinybrowser',
themes : 'simple,advanced',
languages : 'en',
disk_cache : true,
debug : false
}, function(){
isTinyMCE_Loaded = true;
callback();
});
};
BuildWYSIWYG.Full: function(el){
settings.elements = jQuery(el).attr("id");
// Build advanced wysiwyg
if (isTinyMCE_Loaded){
tinyMCE.init(settings);
} else {
BuildWYSIWYG.OnDemand(function(){
tinyMCE.init(settings);
});
}
}
There might be another way. Take a look at this example. http://tinymce.moxiecode.com/examples/example_23.php
You can use the links at the bottom (Show,Hide,Bold,Get Contents etc) as a menu (may require some styling). Then, get the id of the textarea currently in focus and pass it to the menu (#current) and use it to change that textarea.
To achieve what you are describing:
First disable all the indivudual TinyMCE menu items.
Once they are disabled, create your own TinyMCE menu in HTML and style it accordingly.
Determine which TinyMCE textarea in focus
Apply the actions from your new menu to the Textarea that is focused
Now for some code (may require some debugging...)
First, Initialize TinyMCE and disable menus.
tinyMCE configs
({
mode : "textareas",
theme : "advanced",
editor_selector : "editable"
theme_advanced_buttons1 : "",
theme_advanced_buttons2 : "",
theme_advanced_buttons3 : "",
theme_advanced_toolbar_location : "botton",
theme_advanced_statusbar_location : "bottom" });
I think you can also edit the _addToolbars function in tiny_mce/themes/advanced/editor_template_src.js and then pack it.
Then determine the text area that is currently in focus using jQuery bind:
$().ready(function() {
var current;
$('.editable').focus(
current = this.id;
);
$('.editable').blur(
//maybe hide the menu (?)
);
}
Then create the HTML with our textareas and the menu
<form method="post" action="somepage">
<div id="independent_menu">
<!-- The Menu, Please Style Accordingly -->
[Show]
[Hide]
[Bold]
[Get contents]
[Get selected HTML]
[Get selected text]
[Get selected element]
[Insert HTML]
[Replace selection]
</div>
<!-- The Text Areas -->
<textarea class="editable" id="one">Some Text Here</textarea>
<textarea class="editable" id="two">Yet another text area</textarea>
<textarea class="editable" id="three">Final Text Area</textarea>
I did this with an older version of tinymce:
http://tinymce.moxiecode.com/punbb/viewtopic.php?id=10197
http://examples.dtbaker.com.au/code/tinymce/
Haven't re-produced this with the latest version though :(
But basically there's two ways to do it, either:
1) Create your own menu that calls tinymce arguments on the active tinymce editor.
2) Set the tinymce toolbar/menu to be external, so that it appears when you focus an editor. Then using CSS you position each toolbar to appear in the same place. So it looks like there is a single toolbar but in fact it is multiple toolbars appearing in the same place.
Hope that helps.
I am providing solution for this question in case anyone still comes here for one. You can use execCommand to execute various styles of text you like while clicking on your custom buttons. For example:
// bold, italic and underline
$('#bold').click(function(){
tinymce.execCommand('Bold');
});
$('#italic').click(function(){
tinyMCE.execCommand('Italic');
});
$('#underline').click(function(){
tinyMCE.execCommand('Underline');
});
//commands for left align, right align and center align
$('#l-a').click(function(){
tinyMCE.execCommand('JustifyLeft');
});
$('#c-a').click(function(){
tinyMCE.execCommand('JustifyCenter');
});
$('#r-a').click(function(){
tinyMCE.execCommand('JustifyRight');
});
//commands for inserting ul or ol
$('#ul').click(function(){
tinyMCE.execCommand('InsertUnorderedList');
});
$('#ol').click(function(){
tinyMCE.execCommand('InsertOrderedList');
});
where #bold, #italic, #ul etc. are ids of the html elements which you are using to do implement styling. For example:
<button id="bold">B</button>
This button will bold the text, no matter the text is in which instance of tinymce.
Though the only drawback with this functionality is that you will have to do a lot of work for showing the effect on particular button when its on or off. If you are not concerned with that then this will do the trick.
I hope it helps...

Categories

Resources