Open d-uzlov opened 3 years ago
Few more from skin-setup page
I'm not sure if these notes are simply for the future or if these notes require some explaining.
To be explained, and rewritten if necessary.
Few more from skin-setup page.
But i can't find a good way to explain it. TwT
I would say that it almost never makes sense to query raw data from handlers that produce it. Usually raw data is very inconvenient to work with. This mostly applies to FFT results, and intermediate FFT-chain handlers (like BandResampler). Handlers like loudness and peak have transforms option, and ValueTransformer can sometimes be used to transform already useful data, like I did with Loudness example skins.
Btw could you check this?
Source=ID id_string Todo: Check examples validity.
And
UnusedOptionsWarning=false
will make such log messages to disappear.
What kind of messages will still be logged even when UnusedOptionsWarning=false
?
Btw is it okay to compare some options to AudioLevel? that way it would be easier to explain.
Maybe i'll update the examples to contain all possible types, right now RMS type is missing.
Oh, by the way, I didn't have any example for RMS because it's kinda useless for me. In AudioLevel plugin RMS is used to measure loudness, but AudioAnalyzer now have a dedicated Loudness handler, that, IMO, works much better, than RMS. But since Loudness handler is not an RMS, and someone could potentially need exactly RMS, I didn't remove it from documentation. But RMS has no intended uses, it's just there for people who know what they are doing.
Oh, by the way, I didn't have any ... they are doing.
After i add it to the docs, should i label it as deprecated?
After i add it to the docs, should i label it as deprecated?
I don't know. There is nothing wrong with it (unlike the things that I have marked deprecated and removed from documentation), it's just it's not the best choice for a loudness meter, and I don't know if it has some good applications.
I got the idea, a similar explanation would be.. cascades are frames of processed values, and these values are calculated the way you explained above. Correct? QwQ
Yeah, something like this.
Or just in short, this option will hide the errors generated only by doing this:
Processing-ProcessName=channels auto | handlers wave | speed fast
Or this:SomeUndocumentedOption=Something
?
I would love to be able to also catch unknown options on the global rainmeter lever, but rainmeter API doesn't have a way to enumerate all options in a measure, so things like SomeUndocumentedOption=Something
aren't accessible to plugins.
I would love to be able to also catch unknown options on the global rainmeter lever, but rainmeter API doesn't have a way to enumerate all options in a measure, so things like SomeUndocumentedOption=Something aren't accessible to plugins.
Oh, so for now that option only hides Processing-ProcessName=channels auto | handlers wave | speed fast
errors?
For the Child measure page
For the Child measure page
Still WIP, i'll look into this soon.
By the way, I still insist that UpdateRate and WarnTime are options of Threading, and not values of Policy option. The way it is written looks confusing, because description doesn't match real syntax.
But UpdateRate
can't be used without SeparateThread
parameter, that's why i left them in same place.
What is "can happen"? and will it happen in regular Rainmeter update cycle? I mean, if the plugin reconnected to that device, everything will go back to normal? without skin refresh?
In the current version of the plugin this happens automatically when possible. No skin refresh required. Else there wouldn't be these callbacks.
Which notice? a message in logs?
I meant notice in the documentations, the one I suggested to add.
Btw, if possible, can i add you as a project member? just to correct minor mistakes, and i'll take care of actual writing.
Yeah, sure. Though I wouldn't rely on myself to find all mistakes.
Although it's still not clear for me, but gives enough insight to know the issue.
Well, if you have speakers and headphones, and you have set Source=defaultoutput
, then if you pull the headphone jack from the PC, the plugin will automatically connect to speakers. But you you then also pull speakers jack, there will be no audio devices available, and onDeviceDisconnected will be called.
But
UpdateRate
can't be used withoutSeparateThread
parameter, that's why i left them in same place.
There are a lot of options that are not compatible with each other (although most of them are deprecated so they aren't in the documentation). It doesn't mean that some values for these options should be considered independent options. I believe that having a warning about UpdateRate not having an effect is enough. Also, I would not say that "nothing matters unless Policy is set to SeparateThread". I would say that "if Policy is set to UiThread then UpdateRate (only specifically UpdateRate) doesn't matter, because it is controlled by rainmeter".
The main issue fro me is that syntactically there are options and there are value. Documentation is there to tell the user that he should write Policy <value for policy> | UpdateRate <value for update rate>
, and not Policy UpdateRate
(but now according to indentation this is a valid value for Threading option).
I meant notice in the documentations, the one I suggested to add.
Oh, a notice in logs window, got it.
Though I wouldn't rely on myself to find all mistakes.
It's my job to find these, you are a reviewer. \( ̄︶ ̄\)
Well, if you have ... will be called.
Added as an example and committed.
But now according to indentation this is a valid value for Threading option.
That's a horrible error lol, definitely not what i meant.
I fixed them in this commit.
For the Child measure page.
There is no ValueID option in the current version of the plugin. Well, at least it's not documented.
Yeah i didn't find docs for it, although it's still working.
It's not really deprecated, it's just renamed to HandlerName
. If HandlerName option is empty, then ValueID is used, to keep compatibility with old skins.
Btw, in future, can you make this something like, if
HandlerName=ThisHandlerTypeDoesNotProvideIndexing
then automatically ignore theIndex
option and set it to 0?
Yeah, why not.
I never used section variables except when using Lua scripts inside the skin.
As far as I know, in some places in the rainmeter different values of measures are used.
Like, Calc measure uses number value when using its inner syntax for formulas. Most meters also use number value.
Generally speaking, I suspect that most rainmeter users don't know that number value and string value are separate, and one measure can have both. Most people just write [&MeasureName] for everything.
That's why there is a StringValue=Number
option, to allow people to use numbers with without a deep dive into rainmeter section variables system.
That's why there is a StringValue=Number option, to allow people to use numbers with a deep dive into rainmeter section variables system.
StringValue=Number Will make this Child measure provide the retrieved String value of handler as a Numerical value.
Correct? If yes, i feel like that sentence is a bit long and takes time to understand.
Correct? If yes, i feel like that sentence is a bit long and takes time to understand.
Not quite.
the retrieved String value of handler
Generally handlers only have numeric values in the first place. The only "string values" you can get from handlers are from section variables.
Maybe it would be better to say by default string value is a number, and that StringValue=Info
replaces that number with a result of section variable resolve.
Maybe it would be better to say by default string value is a number, and that StringValue=Info replaces that number with a result of section variable resolve.
Hmm..
Is it necessary to mention it in first place?
I thought it's important so i added it. But since it doesn't make a difference for the users then we can remove it all together.
And we can find a simpler phrase for Number
parameter.
Btw can you check Child measure page? i finished documenting it. Except transformations, StringValue
and InfoRequest
options.
This will make sense when we explain HandlerName option.
Maybe we should rearrange options, so that HandlerName is before Processing option. I think for the reader it would make more sense to have a reference to something they have already read than to something in the future.
Note that Child measure can only listen to one Channel at a time. Not documented, is it correct?
Yeah, things like Channel=FL, Right
are not allowed.
HandlerName option used to be called ValueID. It's preferred to use HandlerName Since ValueID is kept just for compatibility with old skins.
I'm not sure if it's worth writing about deprecated options. If someone creates a skin, I think it would be better to only use "modern" options. But I don't have a strong options about this, choose what you like.
An example of a value index would be: ... ...
I don't think these are good examples. First of all, for me it was just a little bit hard to read, and also by separating indices on bin and band values it kinda implies (though not really) that other handlers don't have indices.
I would write something like this:
Many handlers produce arrays of data, and the Index option specifies the index of value in that array. For example:
Generally, only handlers that transform data from FFT produce arrays of data (Like, if you have handler chain FFT → BandResampler → ValueTransformer → TimeResampler, then all four of these will make data arrays). Independent handlers (like Loudness) usually produce only one value, so any index except for 0 will be invalid.
P.S. It's not not directly related, but it's better to try not to use examples with directly getting data from FFT, because its size is dynamic, so anything that gets data from an FFT handler will be unreliable.
Maybe we should rearrange options, so that HandlerName is before Processing option. I think for the reader it would make more sense to have a reference to something they have already read than to something in the future.
~On the other hand this might be confusing, all of a sudden HandlerName
option comes out without knowing how it...~
After thinking, you are right. But to be honest i don't know how to link them together this way, a rewrite is needed.
But I don't have a strong options about this, choose what you like.
There was a reason why i mentioned it, but i forgot it lol. I removed it for less visual noise.
P.S. It's not not directly related, but it's better to try not to use examples with directly getting data from FFT, because its size is dynamic, so anything that gets data from an FFT handler will be unreliable.
I removed old examples and used yours.
Now Child measure page (except transformations) is completed. Only few checks are needed for StringValue
and InfoRequest
options.
i don't know how to link them together this way, a rewrite is needed.
I suggest the following: Place Processing right after HandlerHame, so that they are linked by placing on the page.
Processing
Name of the process to get data from. (!)this option is optional Child measure gets data from specific handler. Usually it's enough to specify HandlerHame option to find a handler. However, it's allowed to have one handler description be used in several processes. In such case each of the processes will have its own copy of such handler, so to HandlerHame alone is ambiguous.
Processing
option allows to resolve this ambiguity. ! here goes example
On the other hand... I'm thinking if I should specifically forbid using the same handler in several processings, just to make it less confusing to the user. It's not that useful after all.
StringValue
Number: Will make this Child measure provide the retrieved String values of handler as a numerical value.(Correct?)
You make it sound like it will use section variable value (from InfoRequest) as a number value. Actually, that's an interesting idea, but that's not true for current version of the plugin and that's probably not what you wanted to say. I would rephrase it as "String value of the measure will match its number value" or "Measure won't have a separate string value".
Example ; Will make this Child measure provide the following: Realtek High Definition Audio
I think we should make clear that this is an example
… provide the name of current audio device, for example: Realtek High Definition Audio
Example
Variable=[InfosMeasure] ; Makes the value of that variable the name of the current Audio Device. ; As example: Realtek High Definition Audio
Though it will work as you explained, this is technically not correct.
In rainmeter variable don't resolve its values. So if you write Variable=[InfosMeasure]
then the value of the variable will be [InfosMeasure]
, and only in the place where you use this variable it will be transformed into some real value, like "Realtek High Definition Audio". And by that point the value of [InfosMeasure] may have changed.
Rainmeter variables are kinda strange.
I think it would be better to use a [!log] call as an example.
By the way. I don't remember if I have specified anywhere what allowed symbols for handler names are. Like, if user is allowed to use special symbols in names. You have recently read the major part of the documentation. Do you remember anything like this?
Btw, here are few notes before releasing this plugin:
Plugin=PluginName
option: Right now we have to reference the plugin name + its version name (Plugin=AudioAnalyzer_1_1
), while it can simply be Plugin=AudioAnalyzer
.This can be improved to be like:
Name
: AudioAnalyzer (without version number or underscores)Version
: 1.x.x (without 64 or 32 bit)Author
: rxtd - 2021 © (the copyright symbol to look cool)And after finishing the docs, we will be ready to distribute the plugin. ^^
Memory leak: This is a big problem since it can happen for any mistake in parameters. It can be annoying if it happened while experimenting with plugin options for first time.
It will certainly be fixed.
Plugin=PluginName
option: Right now we have to reference the plugin name + its version name (Plugin=AudioAnalyzer_1_1
), while it can simply bePlugin=AudioAnalyzer
.
We can rename it. Well, technically plugin name is just a file name. You can rename plugin file whenever you like, and use another name. I could rename the plugin on every release, if I wanted to.
But.
But there is a weight of backward compatibility upon my shoulders.
There are skins that use this plugin. Skins, that will never ever be updated.
And if some another skin uses the same plugin, then the plugin will be updated, and it will use the newest version.
But if the plugin name will change, then old skins will forever use the old version. I don't want this.
We could ask skin authors to include two plugins in their .rmskin packages: AudioAnalyzer and AudioAnalyzer_1_1. But I doubt anyone will do this.
Ideally we would have a centralized plugin repository, and rainmeter would search for updated plugins there. But we don't have one, and I doubt it will be created in the next few decades.
Also ideally we would have some guidelines on plugin names so nobody would name a plugin like me.
It was a very dumb decision to name the plugin like this. But I can not undo this without breaking compatibility with old skins.
P.S. Oh, cool, I have remembered that there once was a plugin named AudioAnalyzer. It had very different syntax, and all the skins using it would break if I were to name a new version just AudioAnalyzer (though, it's unlikely any skin uses it because it only existed few weeks before I replaced it with 1.1 version, but still). So it would have to be something like AudioAnalyzer2. If in any time in the future I will break the compatibility I will certainly rename the plugin. But for now I would like to leave the name as it is: it's dumb but it's tolerable.
P.P.S. It should have probably been a separate issue, and not in this repository, because people who have the same question will never find it here. But whatever.
Name: AudioAnalyzer (without version number or underscores)
Can't be. There is already another plugin with this name. Also, this is not a meta-info from plugin, it's just a file name of the plugin.
Version: 1.x.x (without 64 or 32 bit) Author: rxtd - 2021 © (the copyright symbol to look cool)
Yeah, good idea.
I got you, actually i wanted to do the following,
OnRefreshAction=[!WriteKeyValue SectionName VarName [ChildMeasure] FilePath]
. And tell the user to refresh at least once again (we won't use OnRefreshAction event of course, just an example). Then we use that VarName inSource
option as an example:Source=ID [#VarName]
. I mean that should work right?
Well, it should probably work. I don't think that must be a part of documentation, though. Maybe there could be an example skin that shows how to utilize LUA and section variables for some purposes, where you could use something like this. But not in the main part of the documentation: it's too specialized.
Plz don't hate me :c but i don't think there are a lot of skin, that are In Use, that uses the current version of the plugin, or even the first version.
Well, I understand that my plugins are not that popular, and it's likely due to documentation. By search on rainmeter forum I know that eclectic-tech made few skins and a guide that has AudioAnalyzer 1.1. I don't know how much people are using these, though.
I guess, it's not that big of a deal if plugin name would change as this point. I'm not sure if I'm ready to risk using "AudioAnalyzer" without suffix, though. If I just change name to something new then old skins won't get the updated version of the plugin and that's all. But if I use a name that some incompatible plugin is using, then old skins would break, and that's a much higher price. While there are most likely exactly zero skins using 1.0 version, it is still a risk. Maybe replacing "_1_1" with a short "2" would be a good enough compromise.
Can't be. There is already another plugin with this name.
What? where? i thought you the first who used this name.
I meant the 1.0 version of the plugin. Since it's incompatible, it must be treated as a separate plugin.
it's too specialized.
Sure, that would be in Tips and Code Snippets section.
By search on rainmeter forum I know that eclectic-tech made few skins and a guide that has AudioAnalyzer 1.1. I don't know how much people are using these, though.
About that skin, it was Downloaded 374 times, and its already been a year since it was released. Abour that guide, it's mainly for people who don't wanna touch Lua, and tbh that guide is not functional for something custom. So users who want to make there skins using that guide "may" find using Lua more intuitive than this method.
About when he mentioned your plugin in that guide, he didn't show how to use the plugin itself, actually.. i had no idea what he meant lol, because i didn't use his template (Lua goes brrrrr).
I'm not sure if I'm ready to risk using "AudioAnalyzer" without suffix, though. If I ... good enough compromise. I meant the 1.0 version of the plugin. Since it's incompatible, it must be treated as a separate plugin.
Go for it. Even if you think it's a huge risk. Why? here is the thing.
First, not a lot of users are using skins with the old plugin, so this change is for the greater good.
Second, what in the world will break compatibility with older skins (here i mean the ones with 1.0 version) except Downloading a New music visualizer skin that has a new version of the plugin. The user who will do this know what they are doing, they want to use a New visualizer, so probably the old skins will never see the light in there desktop again.
3rd, v1.1 will never get updated again, okay, how is it going to get updated in first place lol? of course by downloading a skin that has a newer version, and again, how this will happen? when the users search and download a new music visualizer that uses your plugin. The last point has one thing, there would be 2 versions of the plugin in there rainmeter plugins folder (1.1 version and the without prefix version).
But should we worry? it's not like the plugin is huge and takes a lot of space, i already checked and found the whole folder which contains 3 different versions(1.1, 1.1.5, 1.1.5.1(last one is 32bit only)) with each version has 32 and 64bit, takes only 2.1Mb .
Note that we are talking about a fraction of rainmeter community, and i'm pretty sure even this small portion will look for new skins at some point.
Just go with AudioAnalyzer without any prefix, no other plugin used/will use it except yours, why? because i'm sure.
P.P.S. It should have probably been a separate issue, and not in this repository, because people who have the same question will never find it here. But whatever.
When we are ready to release, we can create that issue if necessary.
Hello, i added some warnings in skin setup page and in parent page about the letters that users can use specify names (e.g. Processes, Handlers).
Also i started adding some illustration (right now only Target rate is illustrated with images). I'm planning to add more to explain options and handler types like fft and such. Of course they are credited at the bottom of the page.
Section Variables docs are committed and ready for review. 🚀
The Resolve Function (Function?) takes 2 arguments:
Well, it's up to rainmeter how to call these things. I don't remember what word they use exactly. But for me it pretty much looks like a function.
FirstArgument: (?, sorry i can't find an example :c )
Um, I guess you can pick any argument value from the page. What's wrong with it?
Should i say "makes the child measure return/give 'something', otherwise 'something else'?
I would say that "provides" is the best fit here. Though, child measures have nothing to do with this. I would say that section variables are independent, and child measures just use their syntax for the convenience of the user.
[!Log [&ParentMeasure:Resolve(Device List Output)]] ; Will output: …
I think it worth noting that this example is for the case when user only have 1 output audio device, and more devices will lead to more lines.
Possible values of Form factor are: RemoteNetworkDevice, Speakers, LineLevel, Headphones, Microphone, Headset, Handset, UnknownDigitalPassthrough, SPDIF, DigitalAudioDisplayDevice, "unknown".
Maybe it was not the best choice for ease of writing formatted markdown text, but <unknown>
must have "less" and "more" sumbols on its sides (same goes for sample rate and channels).
Also, maybe it would be better to format all the values as inline code blocks, to emphasize that these are well defined values that must be used as-is. This would also preserve <>
symbols without additional hustle.
Form factor or format?
Form factor is specifically how audio device looks to user. The most reasonable use for this is to show an icon for the device depending on its form factor. Format is about channels and sampling rate.
If Proc is not specified, then the plugin will try to find a process that contains the handler specified in Handler argument.
I guess that's unnecessary since we decided that it would be the best to forbid using the same handler name in several processings, so Proc
option will likely be removed both from here and from child measure.
Um, I guess you can pick any argument value from the page. What's wrong with it?
I mean second arg specifies what infos you want to know about the first arg, but first arg specifies what?
Though, child measures have nothing to do with this.
Typo, i was thinking about InfoRequest
option when writing that.
I think it worth noting that this example is for the case when user only have 1 output audio device, and more devices will lead to more lines.
I copied it from your docs, should i remove it and let users experiment with themselves?
Maybe it was not the best choice for ease of writing formatted markdown text, but
must have "less" and "more" symbols on its sides (same goes for sample rate and channels).
\<> symbols for some reason hide the word inside them in markdown, that's why i didn't use them
Also, maybe it would be better to format all the values as inline code blocks, to emphasize that these are well defined values that must be used as-is. This would also preserve <> symbols without additional hustle.
I can add code-blocks instead of \<> symbols.
P.S i realized i can escape them with a backslash \\<\>, should we go with them or with code-blocks
?
Form factor is specifically how audio device looks to user. The most reasonable use for this is to show an icon for the device depending on its form factor. Format is about channels and sampling rate.
Oh, so they are different args. I thought it was a typo.
I guess that's unnecessary since we decided that it would be the best to forbid using the same handler name in several processings, so Proc option will likely be removed both from here and from child measure.
I'll remove it.
I mean second arg specifies what infos you want to know about the first arg, but first arg specifies what?
I would say that the first arg specifies the type of information you want to get. [Information about] Current Device
, Device List
, Value
[of a handler], etc.
I copied it from your docs, should i remove it and let users experiment with themselves?
No, I just mean that we should note that only one of the lines look that way. I wouldn't even say that this is confusing, it's just looks a bit incomplete to me.
P.S i realized i can escape them with a backslash \<>, should we go with them or with
code-blocks
?
I would say to go with the code blocks, just to show that these are exact values, like names of options or channel names.
One issue to discuss everything that's difficult to understand in current version of documentation.
Click to expand
>Channels are present in the audio device(?) From .txt: "list of channels that this processing must process ~~of~~ **_if_** they are present in the audio device". I guess I should have paid more attention to typos. Sorry. In case this is still not clear: I wanted to say that `Channels` option specifies all possible channels that this Process can use, but if some of them aren't present in the audio device (for example, 2.0 headphones don't have Center, LFE, Back and side channels) they won't be present in the Process. --- >TargetRate(Optional): Specify the sample rate of the processed audio stream.(?) What are the issues with this option? --- >Todo: "process description" term still not clear "process description" is exactly 4 options: Channels, Handlers, TargetRate and Filter. It wasn't intended to have any more meaning than this. >Specify description of a sound handler.(?) As with "process description", it's just a set of options. --- >UnusedOptionsWarning >Todo: Can it be renamed to LogErrors? also is the syntax correct? It only affects options that the plugin didn't read. Other log messages are not suppressed with `UnusedOptionsWarning`. For example, if you write `Processing-proc2=channels auto | handlers wave | speed fast`, then there will be a log message `Processing proc2: unused options: [speed]`, and `UnusedOptionsWarning=false` will make such log messages to disappear. Intended usage of this option is to clear the log when you, for some strange reason, have some unused options that you don't want to delete. For me this mostly happens when I want to disable some option, but I don't want to delete it. So I can temporarily rename `filter` to `filter1`, and it won't be parsed. --- >Threading >Policy: Specify the way the plugin will work. I don't know what happened here, but `UiThread` and `SeparateThread` are values of option `Policy`, but they are for some reason formatted as separate options. >Means that each process(?) will create its own working thread. No, there will be only one background thread, that will process everything. --- >OnDeviceDisconnected >Device that was being captured is not in exclusive mode(?). "Device that was being captured is ~~not~~ **_now_** in exclusive mode". I'm sorry, I'm very bad at typos. >OnDeviceListChange >Device was disabled or disconnected.(?) >Or disconnected? what's the diffrence between this and OnDeviceDisconnected event? OnDeviceDisconnected is called when the device you are using was disconnected from the plugin. Nothing to do with the device physical disconnection, it's just that plugin can no longer connect to it. In fact, IIRC, OnDeviceDisconnected is only called when the plugin become disconnected from the device. When one device is disconnected but another is available, then plugin seamlessly switches to that second device and only onDeviceChange is called. OnDeviceListChange is called when _any_ device changed. Changes include, for example, when user pulled the headphone jack from the PC. When OnDeviceDisconnected is called, then OnDeviceListChange is also likely to be called, but it's not guaranteed, and it doesn't work the other way around. ---There are also several notes, that start with "TODO". I'm not sure if these notes are simply for the future or if these notes require some explaining, like above.