[링크] 아기와 고양이, 사이좋게 잘 지내는 방법
'냥이' 카테고리의 다른 글
| [펌] 고양이 (0) | 2016.11.08 |
|---|---|
| [링크] [BBC다큐] 고양이의 "야옹"과 "그르렁" (0) | 2016.10.24 |
| [링크] 고양이를 처음 키우게 된 당신에게 (0) | 2016.10.24 |
| [링크] 고양이 간지럼 태우는 법을 아시나요? (0) | 2016.10.24 |
| 노르웨이 숲고양이 성격과 키우는 법 (0) | 2014.11.25 |
| [펌] 고양이 (0) | 2016.11.08 |
|---|---|
| [링크] [BBC다큐] 고양이의 "야옹"과 "그르렁" (0) | 2016.10.24 |
| [링크] 고양이를 처음 키우게 된 당신에게 (0) | 2016.10.24 |
| [링크] 고양이 간지럼 태우는 법을 아시나요? (0) | 2016.10.24 |
| 노르웨이 숲고양이 성격과 키우는 법 (0) | 2014.11.25 |
Have you ever found yourself wishing a built-in Unity class had some functionality that isn’t there? C#extension methods are the answer!
In this article, I’ll teach you how to use extension methods to add functionality to existing classes, no matter if they’re built-in Unity types, types defined in a third-party plugin, or even types defined in an Asset Store package which you could edit but you’re (rightly) worried about later package updates stomping your “patch”.
Seemingly obvious API omissions can be frustrating, but extension methods let you “fix” just about any API to your liking.
Hit the jump for all the details!
Imagine you need a way to set the layer of a GameObject and all its children, but there’s no GameObject.SetLayerRecursively() available. You could embed a loop in your code:
// Do some work.
// Set the layer of this GameObject and all its children.
gameObject.layer = someLayer;
foreach(Transform t in transform)
t.gameObject.layer = someLayer;
// Do some more work.This will work fine, although it’s not the cleanest thing in the world, and you’ll need to copy these lines of code around to every place where you want to do this operation. It would be better to encapsulate that code in a function, and make that function available to everyone via a “helper” class:
public class GameObjectHelper
{
public static void SetLayerRecursively(GameObject gameObject, int layer)
{
gameObject.layer = someLayer;
foreach(Transform t in transform)
t.gameObject.layer = someLayer;
}
}
public class Test : MonoBehaviour
{
void Start()
{
GameObjectHelper.SetLayerRecursively(gameObject, someLayer);
}
}This works fine too, but it can be easy to forget to use the helper class to invoke a function that feels like it belongs in GameObject itself. Wouldn’t it be nicer if you could just do this?
gameObject.SetLayerRecursively(someLayer);As it turns out, C# lets you make this happen!
Extension methods are declared just like regular functions, except that a) they must be static, b) they must be declared inside a non-generic, non-nested, static class, and c) they include a special syntax for their first argument, which is a reference to the calling object:
public static class GameObjectExtensions
{
public static void SetLayerRecursively(this GameObject gameObject, int layer)
{
// Implementation goes here
}
}Though declared as static, this is invoked as if it were an instance method:
myGameObject.SetLayerRecursively(someLayer);Note that when we call the method we actually omit the first argument and skip straight to the second. Take another look at the method declaration above. See how the first argument is declared using the “this” keyword? That’s what tells the compiler to infer that argument as the calling object; in this case, myGameObject.
That’s actually all there is to it. Extension methods are easy!
For what it’s worth, I like to organize my extension methods into classes named ClassNameExtensions. So I have GameObjectExtensions, TransformExtensions, ColorExtensions, and so on. There’s nothing that says you have to do this; I just like the organization. You could pack them all together into a single Extensions class if you prefer, or any other kind of organization you want. Just remember that extensions methods must be declared inside a non-generic, non-nested, static class; the compiler will complain otherwise.
Extension methods can add to an existing class, but they cannot override existing methods. For example, if you declared this:
public static class GameObjectExtensions
{
public static Component GetComponent(this GameObject gameObject, Type type)
{
Debug.LogError(“LOL, you got trolled”);
}
}…the compiler would basically ignore you. The rule for multiple method declarations using the same signature is: instance methods always take precedence over extension methods.
To extend a type, you’ll need make sure it’s in scope with the “using” directive. If you’re extending any built-in Unity type, you’re covered by virtue of the “using UnityEngine” that’s a standard entry in most Unity scripts. If you’re extending an editor type, you’ll need to add “using UnityEditor”, just like you would if you were calling that type. If you’re extending a type from a third-party plugin, you may need to import a namespace; check the plugin’s documentation (or source code, if you have it) for details.
I’ve already mentioned that extension methods must be declared inside a non-generic, non-nested, static class, which means you can’t just drop them in willy-nilly wherever you want. In practice, this “limitation” turns out to be a useful organizing device. You can certainly argue that this is virtually identical to the “helper class” example at the top of this article, and in terms of implementation effort that’s probably true; the difference is that with extension methods you get a cleaner, more normalized calling syntax. This really comes down to personal preference.
For the rest of this article, I’ll share some useful extension methods I’ve written over the past few months. Feel free to incorporate these into your own codebase and modify them at-will. (But don’t just copy-paste them into a text file and try to sell it on the Asset Store; that would make you a horrible person.)
I use the excellent 2D Toolkit for UI, and I use a two-camera setup: one camera for the scene, one camera for the UI. In order to make the UI camera render only UI objects, all the UI objects need to be on a UI layer. When I create UI objects from script I need to set that layer, and often I’m creating objects with children (like a button with a child sprite and a child text label).
It’d be nice to have a way to set the layer for this entire hierarchy with a single function call (you’ll recognize this as the example at the top of this article). Here’s what the call looks like:
myButton.gameObject.SetLayerRecursively(LayerMask.NameToLayer(“UI”));And here’s that extension method:
// Set the layer of this GameObject and all of its children.
public static void SetLayerRecursively(this GameObject gameObject, int layer)
{
gameObject.layer = layer;
foreach(Transform t in gameObject.transform)
t.gameObject.SetLayerRecursively(layer);
}While we’re doing things recursively, wouldn’t it be nice if we could enable/disable just the renderers, or just the colliders, for an entire hierarchy? This can be useful for UI, but it can also be useful in the scene. Imagine a complex hierarchy that defines a really fancy animated force field, and a game mechanic whereby you can switch your avatar’s polarity, allowing passage through force fields of a particular color. When you switch polarity, you’d loop through the matching force fields and disable their colliders, like this:
foreach(ForceField forceField in forceFields)
forceField.gameObject.SetCollisionRecursively(false);Here’s that extension method:
public static void SetCollisionRecursively(this GameObject gameObject, bool tf)
{
Collider[] colliders = gameObject.GetComponentsInChildren<Collider>();
foreach(Collider collider in colliders)
collider.enabled = tf;
}And the same principle applies for renderers:
public static void SetVisualRecursively(this GameObject gameObject, bool tf)
{
Renderer[] renderers = gameObject.GetComponentsInChildren<Renderer>();
foreach(Renderer renderer in renderers)
renderer.enabled = tf;
}It’s easy to search for child components using GameObject.GetComponentsInChildren(), but what if you have a have hierarchy in which you have lots of instances of a type, and you only want those instances which have a particular tag? In my case, I had a compound object with numerous renderers, and I needed to drive a material color on a subset of those renderers tagged as “Shield”.
This proved convenient:
m_renderers = gameObject.GetComponentsInChildrenWithTag<Renderer>("Shield");Here’s that extension method:
public static T[] GetComponentsInChildrenWithTag<T>(this GameObject gameObject, string tag)
where T: Component
{
List<T> results = new List<T>();
if(gameObject.CompareTag(tag))
results.Add(gameObject.GetComponent<T>());
foreach(Transform t in gameObject.transform)
results.AddRange(t.gameObject.GetComponentsInChildrenWithTag<T>(tag));
return results.ToArray();
}I noted earlier that extension methods must be declared inside non-generic classes. That doesn’t mean the extension method itself can’t be generic, however! When we call this method we replace T with the type we’re interested in — in the preceding call example, it was Renderer — and that type is used for each occurrence of T in the method implementation. The “where” keyword specifies that T must be of type Component or a type derived from Component (the compiler will throw an error otherwise).
See this MSDN article for more information about generics.
It’s all well and good to get components in children, but sometimes you need to search up. A common case I run into is when figuring out what to do with a collision result. I have a Player type, and its hierarchy is made up of several GameObjects which represent visuals, colliders, equipped items, and so on. Typically when I get a collision result on a player, the collider is bound to a child GameObject, so I can’t just do GetComponent
So now I do this:
Player player = collider.gameObject.GetComponentInParents<Player>();Here’s that extension method:
public static T GetComponentInParents<T>(this GameObject gameObject)
where T : Component
{
for(Transform t = gameObject.transform; t != null; t = t.parent)
{
T result = t.GetComponent<T>();
if(result != null)
return result;
}
return null;
}Just like Unity has both GameObject.GetComponentInChildren (singular) and GameObject.GetComponentsInChildren (plural), I also created a version that gets all components in parents:
public static T[] GetComponentsInParents<T>(this GameObject gameObject)
where T: Component
{
List<T> results = new List<T>();
for(Transform t = gameObject.transform; t != null; t = t.parent)
{
T result = t.GetComponent<T>();
if(result != null)
results.Add(result);
}
return results.ToArray();
}Note: it would be trivial to create a GetComponentsInParentsWithTag, but I haven’t run into a need for it yet. If you’d like to exercise your newfound knowledge of extension methods, this might be a good exercise. :)
Here’s one whose omission is particularly perplexing. You can get the layer a GameObject is on, which is useful for both rendering and collision purposes, but there’s no easy way to figure out the set of layers that GameObject can collide against.
I ran into this when implementing weapons. Projectile-based weapons are simple: they get a Rigidbody and a Collider of some sort, and the collision system handles everything for me. But a rail gun-like weapon is a different story: there’s no Rigidbody, just a script-invoked raytest. You can pass a collision mask — a bitfield — into a raytest, but what if you want the collision mask to be based on the weapon’s layer? It’d be nice to set some weapons to “Team1” and others to “Team2”, perhaps, and also to ensure your code doesn’t break if you change the collision matrix in the project’s Physics Settings.
Really, I wanted to just do this:
if(Physics.Raycast(startPosition, direction, out hitInfo, distance,
weapon.gameObject.GetCollisionMask())
)
{
// Handle a hit
}That raycast will only hit objects which the calling weapon is allowed to collide with, based on its layer and the project’s collision matrix.
Here’s that extension method:
public static int GetCollisionMask(this GameObject gameObject, int layer = -1)
{
if(layer == -1)
layer = gameObject.layer;
int mask = 0;
for(int i = 0; i < 32; i++)
mask |= (Physics.GetIgnoreLayerCollision(layer, i) ? 0 : 1) << i;
return mask;
}Note the optional “layer” argument. If omitted, it uses the layer of the calling GameObject, which is the most common/intuitive case (for me, at least). But you can specify a layer and it’ll hand you the collision mask for that layer instead.
I often find myself wanting to modulate the alpha value of a color without changing the color itself, for blinking/pulsing effects. Because Color is a struct, and structs in C# are immutable, you can’t simply assign color.a; you’ll get a compiler error. Fortunately, extension methods can extend structs as well as classes:
public static Color WithAlpha(this Color color, float alpha)
{
return new Color(color.r, color.g, color.b, alpha);
}This method makes modulating a color’s alpha clean and simple:
GUI.color = desiredColor.WithAlpha(currentAlpha);There really aren’t any. Extension methods are a compile-time device; once you reach runtime, they look and act just like any other method call. So it doesn’t matter whether you write an extension method or an explicit helper class; as long as the guts of the method are identical, both implementations should perform identically. You could theoretically squeeze a vanishingly tiny bit of performance out of simply inlining all the code, avoiding the overhead of any function call at all, but in this day and age that’s completely pointless to worry about unless you’re calling the function millions of times.
Extension methods are mainly useful as a way of cleaning up and normalizing your code. They have little or no effect on the behavior of that code.
I hope this article has been clear and useful. Extension methods are one of my favorite features of C#, because I’m a bit obsessive about having clean, easy-to-read code and they can really help make that happen. Of course, there’s more than one way to skin a cat, and I’m by no means suggesting that extension methods are the right or only way to do things. You can certainly argue that making an explicit helper class containing regular static functions — like GameObjectHelper.SetActiveRecursively() in the example at the top of this article — is just as good as an extension method-based implementation of the same; they’re six of one, half-dozen of another. I prefer the extension method approach because it feels like a natural and intuitive API extension, rather than a “bolt-on”, but that’s strictly a matter of personal preference.
Like every coding practice, extension methods are just one tool in the toolbox. But I encourage you to give them a shot!
(Oh and by the way: I'm available for contract work doing the sort of things you just read about. Hit me up if you're interested!)
[출처] http://www.third-helix.com/2013/09/30/adding-to-unitys-builtin-classes-using-extension-methods.html
| [펌] Find objects with DontDestroyOnLoad (0) | 2021.11.26 |
|---|---|
| [Unity] Play Streaming Music From Server (0) | 2018.02.06 |
| 일괄적으로 Texture Import Setting 변경 (0) | 2015.01.30 |
| Extension Methods (0) | 2014.08.18 |
| Nullable Types (0) | 2014.08.18 |
유니티3D_Android dll파일 난독화 가이드
(사용툴 : Spices.Net)
[파일]
BS_Unity3D_Obfuscate_Guide_20131220_v0.1.odt
1. 난독화할 dll파일
APK파일을 디컴파일or압축해제를 하면 Asset폴더 내부에 dll파일이 들어있다.
(유니티 프로젝트의 경우 \assets\bin\Data\Managed\)
난독화할 파일은 Assembly-CSharp.dll
2. Spices.Net 툴을 사용하여 난독화하기
http://www.9rays.net/Downloads.aspx 에서
Spices.Net Obfuscator → Spices.Net Free Evaluation 다운로드
Spices.Net 실행후 폴더모양 눌러서 Assembly-CSharp.dll 파일 오픈
최상위 경로에서 마우스 오른클릭을 하면 메뉴들이 나오는데 Obfuscation Options에서 난독화 설정을 해줄 수 있다.
Members 내부에 있는 설정들이 가장 큰 비중을 차지하는것으로 보인다.
Members 설정으로 전체적으로 내부설정들을 한번에 바꿀수도 있고
하나하나 바꿔줄 수도 있다.
Methods와 public옵션이 클래스명과 메소드명을 바꿔주는 설정인데 난독화시 가장 효과가 좋은 설정중 하나이다.
(해당설정 적용시 짜여진 소스 구조에 따라서 작동이 안되는 경우가 있다.
Controll Flow 라는 함수 내부 구조를 바꿔주는 난독화부분은 이 툴에서 아직 찾지 못하였음
Obfuscation Options 설정이 끝났으면 다시 메뉴를 열어서 Obfuscate!를 선택하면 .iloprj 라는 확장명의 파일 저장경로 확인창이 뜨는데 바로 저장을 해주면 dll파일 경로로 저장된다.
(툴관련 정보 저장파일인듯 하다)
경로설정이 완료되면 난독화가 진행되고 정상적으로 난독화가 완료되면 “dll파일 경로\Output\”안에 난독화된 Assembly-CSharp.dll 파일이 생성된다.
난독화된 파일을 기존 dll파일 경로에 덮어씌워준후 다시 컴파일 해주면 작업이 완료된다.
*난독화 적용전 .dll 디컴파일 결과
*난독화 적용후 .dll 디컴파일 결과(Members Full옵션 적용)
[출처]
| [Asset] Obfuscator (2) | 2017.11.17 |
|---|---|
| [펌] 기본 변수 저장시 암호화 (0) | 2016.05.23 |
| [펌] Playerprefs 암호화 (0) | 2016.05.23 |
| C# AES 암복호화 알고리즘 (0) | 2014.03.29 |
| 안드로이드에서 암호화 팁 - 에셋번들 암호화 (0) | 2014.02.28 |
| [펌] [outlook 2013] 본인 자동 숨은 참조 (0) | 2017.01.05 |
|---|---|
| [펌] 샤오미 Yi Camera 속도 문제 해결 방법 (0) | 2016.11.15 |
| [링크] 텔레그램 지진 알림 받는법, 단순하지만 정확한 지진희 알림 봇 (0) | 2016.10.05 |
| [펌] 랜선의 종류와 구분 (UTP/STP/FTP 차이점) (0) | 2016.08.16 |
| [펌] apk파일 디컴파일하기 (0) | 2016.07.29 |
시놀로지 NAS를 사용중입니다. 제가 샀던 IT기기중 만족도가 2번째로 높은 제품이네요...(첫번째는 아이패드2 입니다.. ^^) 시놀로지 NAS가 IP캠의 연동을 지원해서 IP캠을 연동하면 시놀로지 APP을 통해서 실시간으로 보거나 감시 영상을 볼수 있습니다. 문제는 연동되는 IP캠이 10만원 이상으로 고가라서 사기가 망설였습니다. 그런데 얼마전 카페에서 USB웹캠으로 이 기능이 된다는 글을봤습니다. http://forum.synology.com/enu/viewtopic.php?p=191016#p191016 제가 가지고 있던 로지텍 캠이 하나 있어서 바로 설치해 봤습니다.. 안되더군요... Logitech QuickCam Communicate STX를 가지고 있는데..지원하지 않는 모델입니다. 그래서 되는 제품을 찾았죠.. Logitech Webcam C250 이 제품이 벌크로 1만5천원에 올라와 있더군요.. 바로 질렀습니다. 연결했더니 바로 인식하네요... 음성이 들리지는 않지만.. 핸드폰이나, PC, 아이패드에서 집안의 상황을 볼수있어서 좋네요.. 얼마전 집에 전화했는데, 와이프가 한 30분 전화를 받지 않아서... 좀 걱정되서.....(요즘 세상이 좀 그래서...) 와이프는 사생활 침해라고 뭐라뭐라 하는데.... 걱정되서 그런다... 그렇게 무마하고 있습니다.. 어째든 시놀로지 NAS사용자들 중에서 저렴하게 CCTV구축할려고 하시는 분은 참고하세요.. 참... Intel CPU는 잘 안된다는 이야기도 있네요.. 제꺼는 212j 모델입니다. 포럼 보니까 가능한기종 : 0x0802 9 Logitech Webcam C200 0x0804 9 Logitech Webcam C250 0x0805 9 Logitech Webcam C300 0x0807 9 Logitech Webcam C500 0x0808 9 Logitech Webcam C600 0x0809 9 Logitech Webcam Pro 9000 0x080A 9 Logitech Portable Webcam C905 0x08C1 Logitech QuickCam Fusion 0x08C2 Logitech QuickCam Orbit MP 0x08C2 Logitech QuickCam Sphere MP 0x08C3 Logitech QuickCam for Notebooks Pro 0x08C5 Logitech QuickCam Pro 5000 0x08C7 Cisco VT Camera II 0x08C9 Logitech QuickCam Ultra Vision 0x08CA Logitech QuickCam Fusion 0x08CB Logitech QuickCam for Notebooks Pro 0x08CC Logitech QuickCam Orbit MP 0x08CC Logitech QuickCam Sphere MP 0x08CE Logitech QuickCam Pro 5000 0x0990 8 Logitech QuickCam Pro 9000 for Business 0x0990 9 Logitech QuickCam Pro 9000 0x0990 9 Logitech QuickCam Pro 9000 for Business 0x0991 8 Logitech QuickCam Pro for Notebooks 0x0991 8 Logitech QuickCam Pro for Notebooks for Business 0x0991 9 Logitech QuickCam Pro for Notebooks 0x0991 9 Logitech QuickCam Pro for Notebooks for Business 0x0994 8 Logitech QuickCam Orbit AF 0x0994 8 Logitech QuickCam Sphere AF 0x0994 9 Logitech QuickCam Orbit AF 0x0994 9 Logitech QuickCam Sphere AF 0x09A2 Logitech QuickCam Communicate Deluxe 0x09A2 Logitech QuickCam Communicate S7500 0x09A4 Logitech QuickCam E 3500 0x09A6 Logitech QuickCam Vision Pro 0x09C1 Logitech QuickCam Deluxe for Notebooks 0x09C1 Logitech QuickCam Deluxe for Notebooks for Business Supported -------------------------------------------------------------------------------------- 불가능한기종 : "Logitech QuickCam Express Dexxa Webcam" Logitech QuickCam Web "Logitech QuickCam Express Logitech QuickCam for Notebooks Labtec WebCam" Acer OrbiCam (Built-in notebook camera) Acer OrbiCam (Built-in notebook camera) "Logitech QuickCam Connect Logitech QuickCam E 2500" Logitech QuickCam IM Labtec Webcam Plus Logitech QuickCam IM Logitech QuickCam Express Plus Logitech QuickCam Image Logitech QuickCam for Notebooks Deluxe Labtec Notebook Pro Logitech QuickCam IM Logitech QuickCam Communicate STX Logitech QuickCam for Notebooks "Logitech QuickCam Easy Logitech QuickCam Cool Logitech QuickCam Connect (China)" "Logitech QuickCam Pro Logitech QuickCam Pro 3000" Logitech QuickCam Pro for Notebooks Logitech QuickCam Pro 4000 Logitech QuickCam Zoom Logitech QuickCam Zoom "Logitech QuickCam Orbit Logitech QuickCam Sphere" Cisco VT Camera Logitech ViewPort AV100 Logitech QuickCam Pro 4000 Logitech QuickCam Zoom Logitech QuickCam Communicate STX Logitech QuickCam for Notebooks Deluxe "Logitech QuickCam IM Logitech QuickCam Connect" Logitech QuickCam Messenger Logitech QuickCam for Notebooks Logitech QuickCam Messenger Logitech QuickCam Express Labtec WebCam Logitech QuickCam Communicate Logitech QuickCam Communicate Logitech QuickCam Express Labtec WebCam Logitech QuickCam Live Logitech QuickCam Express Labtec WebCam Logitech QuickCam for Notebooks Labtec WebCam Plus Logitech QuickCam Chat Logitech QuickCam Express Logitech QuickCam Chat "Logitech QuickCam Express Logitech QuickCam Go" --------------------------------------------------------------------------------------- 이르케 나오네요.. 다들 가지고 계신것 있으시면 참고하시면 될듯 합니다. http://clien.career.co.kr/cs2/bbs/board.php?bo_table=lecture&wr_id=128668&sca=&sfl=wr_subject&stx=%EC%8B%9C%EB%86%80 [강좌] 시놀로지 NAS에서 안쓰는 USB웹캠을 IP카메라로 인식시키기...시놀로지 NAS에서 안쓰는 USB웹캠을 IP카메라로 인식시켜서 Surveilance Station을 활용하는 방법이 있습니다. 어느 외국 분께서 관련 오픈소스를 활용해 시놀로지 써드파티 SPK로 개발하셨구요. 해당 SPK는 http://forum.synology.com/enu/viewtopic.php?p=191016#p191016 에서 다운로드 가능합니다. 시스템 요구사항은 옮기자면... - ARM베이스 시놀로지 NAS - 로지텍, MS 등 USB 표준 비디오 클래스를 지원하는 웹캠 - 크롬, 파이어폭스 등의 웹브라우저 위와 같구요. ARM베이스만 가능하다고 하지만 개발자분이 해당 SPK 소스를 공개해서 다른 회원분이 인텔 ATOM CPU용으로도 컴파일해놓으셨네요. (다운로드 링크는 http://forum.synology.com/enu/viewtopic.php?f=190&t=49790&start=45#p199716 ) 사용방법은 http://forum.synology.com/enu/viewtopic.php?p=191016#p191016 링크에 스크린샷과 함께 자세히 설명되어있습니다. 간단히 옮기자면 1. 패키지센터에서 다운로드받은 SPK를 설치. 2. Surveillance Station 활성화 및 IP Camera추가 3. 즐거운 감시생활. IP카메라 추가는 아래와 같이 IP: 127.0.0.1 Port: 5000 <- 이 부분은 시놀로지 NAS 디폴트 포트이고 변경하셨다면 그걸로 넣어주시면 됩니다 Brand: [user defined] Source path: webman/3rdparty/webcam/webcam.cgi No username and password needed 물론 웹캠은 Synology NAS에 있는 USB포트에 연결하셔야 됩니다. 이렇게 하면 정상적으로 IP카메라로 연결되어 Surveillance Station 기능을 사용하실수 있습니다. (MJPEG고정, 동작인식 녹화 가능, 해상도는 웹캠디폴트해상도 고정 (HD급 웹캠은 저장용량이 너무 커지는 단점아닌 단점이 있습니다?)) Surveilance Station의 단점으로는 NAS가 슬립모드로 진입되지 않습니다. (동작인식때만 녹화를 하더라도) 그 이유는 안정적인 녹화를 위해서 그렇다고 하네요. 그럼 즐거운 NAS생활 되세요~ 시스템 요구사항은 옮기자면... - ARM베이스 시놀로지 NAS - 로지텍, MS 등 USB 표준 비디오 클래스를 지원하는 웹캠 - 크롬, 파이어폭스 등의 웹브라우저 위와 같구요. ARM베이스만 가능하다고 하지만 개발자분이 해당 SPK 소스를 공개해서 다른 회원분이 인텔 ATOM CPU용으로도 컴파일해놓으셨네요. (다운로드 링크는 http://forum.synology.com/enu/viewtopic.php?f=190&t=49790&start=45#p199716 ) 사용방법은 http://forum.synology.com/enu/viewtopic.php?p=191016#p191016 링크에 스크린샷과 함께 자세히 설명되어있습니다. 간단히 옮기자면 1. 패키지센터에서 다운로드받은 SPK를 설치. 2. Surveillance Station 활성화 및 IP Camera추가 3. 즐거운 감시생활. IP카메라 추가는 아래와 같이 IP: 127.0.0.1 Port: 5000 <- 이 부분은 시놀로지 NAS 디폴트 포트이고 변경하셨다면 그걸로 넣어주시면 됩니다 Brand: [user defined] Source path: webman/3rdparty/webcam/webcam.cgi No username and password needed 물론 웹캠은 Synology NAS에 있는 USB포트에 연결하셔야 됩니다. 이렇게 하면 정상적으로 IP카메라로 연결되어 Surveillance Station 기능을 사용하실수 있습니다. (MJPEG고정, 동작인식 녹화 가능, 해상도는 웹캠디폴트해상도 고정 (HD급 웹캠은 저장용량이 너무 커지는 단점아닌 단점이 있습니다?)) Surveilance Station의 단점으로는 NAS가 슬립모드로 진입되지 않습니다. (동작인식때만 녹화를 하더라도) 그 이유는 안정적인 녹화를 위해서 그렇다고 하네요. 그럼 즐거운 NAS생활 되세요~ 시놀로지 NAS에서 안쓰는 USB웹캠을 IP카메라로 인식시켜서 Surveilance Station을 활용하는 방법이 있습니다. 어느 외국 분께서 관련 오픈소스를 활용해 시놀로지 써드파티 SPK로 개발하셨구요. 해당 SPK는 http://forum.synology.com/enu/viewtopic.php?p=191016#p191016 에서 다운로드 가능합니다. 시스템 요구사항은 옮기자면... - ARM베이스 시놀로지 NAS - 로지텍, MS 등 USB 표준 비디오 클래스를 지원하는 웹캠 - 크롬, 파이어폭스 등의 웹브라우저 위와 같구요. ARM베이스만 가능하다고 하지만 개발자분이 해당 SPK 소스를 공개해서 다른 회원분이 인텔 ATOM CPU용으로도 컴파일해놓으셨네요. (다운로드 링크는 http://forum.synology.com/enu/viewtopic.php?f=190&t=49790&start=45#p199716 ) 사용방법은 http://forum.synology.com/enu/viewtopic.php?p=191016#p191016 링크에 스크린샷과 함께 자세히 설명되어있습니다. 간단히 옮기자면 1. 패키지센터에서 다운로드받은 SPK를 설치. 2. Surveillance Station 활성화 및 IP Camera추가 3. 즐거운 감시생활. IP카메라 추가는 아래와 같이 IP: 127.0.0.1 Port: 5000 <- 이 부분은 시놀로지 NAS 디폴트 포트이고 변경하셨다면 그걸로 넣어주시면 됩니다 Brand: [user defined] Source path: webman/3rdparty/webcam/webcam.cgi No username and password needed 물론 웹캠은 Synology NAS에 있는 USB포트에 연결하셔야 됩니다. 이렇게 하면 정상적으로 IP카메라로 연결되어 Surveillance Station 기능을 사용하실수 있습니다. (MJPEG고정, 동작인식 녹화 가능, 해상도는 웹캠디폴트해상도 고정 (HD급 웹캠은 저장용량이 너무 커지는 단점아닌 단점이 있습니다?)) Surveilance Station의 단점으로는 NAS가 슬립모드로 진입되지 않습니다. (동작인식때만 녹화를 하더라도) 그 이유는 안정적인 녹화를 위해서 그렇다고 하네요. 그럼 즐거운 NAS생활 되세요~ Re: USB Webcam support packageThe Intel package supports now all three architectures of the Intel processors: x86, Bromolow and Cedarview. DSM 4.0 https://dl.dropbox.com/u/30720628/webcam-intel.zip DSM 4.1 http://dl.dropbox.com/u/30720628/webcam-intel-41.zip For anyone experiencing problems with webcam package after upgrading to the newest DSM 4.1-2661 there is another revision of the very same package, so just in case: http://dl.dropbox.com/u/30720628/webcam-intel-41-rev2.zip Enjoy. All credits go to unr3al2 from http://www.pronas.pl Last edited by JustJackLDN on Sun Nov 18, 2012 5:45 pm, edited 6 times in total. |
[출처] http://shimss.ipdisk.co.kr/g5s/bbs/board.php?bo_table=s11&wr_id=724
| [링크] LG TV에서 Synology NAS 동영상 플레이 관련 (1) | 2018.10.23 |
|---|---|
| [펌] 시놀로지 나스(nas) DS note PC버전 (0) | 2018.01.18 |
| [링크] 사진 클라우드 나스 포토 스테이션 (0) | 2016.08.15 |
| [링크] 시놀로지(Synology) 자료 많은 곳 (1) | 2016.08.12 |
| Synology NAS에서 SVN Server 설정 (0) | 2016.08.12 |
首先原帖子在这里:
http://game.ceeger.com/forum/read.php?tid=1383
这楼主做得非常好了,我都不知道怎么优化才好,但是本人是厌恶OnGUI主义者,所以决定要把一切OnGUI的东西根除...
然后附加了镜面效果,看着还行,不说那么多先来个图:


下面是NGUI的排布

主要代码,红色为修改的部分
using UnityEngine;
using System.Collections;
using System.Collections.Generic;
public class NGUICoverFlow : MonoBehaviour {
private List<GameObject> photos = new List<GameObject>();
private int photosCount = 5;
private int currentIndex = 0;
private float MARGIN_X = 3f; //plane 之间的间隔
private float ITEM_W = 10f; //plane长宽为10M(10个单位长度)
private float sliderValue = 4f;
public UISlider uiSlider;
void Start()
{
loadImages();
//uiSlider.numberOfSteps = photosCount; //这里可设成Steps模式 随个人喜好
}
void loadImages()
{
for (int i = 0; i < photosCount; i++)
{
GameObject photo = GameObject.CreatePrimitive(PrimitiveType.Plane);
photos.Add(photo);
photo.layer = 14; //我的相片全部作为一个单独的层 这样镜面渲染就好办了
photo.transform.eulerAngles = new Vector3(-90f, 0f, 0f);
photo.transform.localScale = new Vector3(1.5f, 1f, -1f); //根据图片设定长宽比,z:-1,使图正向
photo.renderer.material.mainTexture = Resources.Load("photo" + i.ToString(), typeof(Texture2D)) as Texture2D;
photo.transform.parent = gameObject.transform;
}
moveSlider(photos.Count / 2);
}
void moveSlider(int id)
{
if (currentIndex == id)
return;
currentIndex = id;
for (int i = 0; i < photosCount; i++)
{
float targetX = 0f;
float targetZ = 0f;
float targetRot = 0f;
targetX = MARGIN_X * (i - id);
//left slides
if (i < id)
{
targetX -= ITEM_W * 0.6f;
targetZ = ITEM_W * 3f / 4;
targetRot = -60f;
}
//right slides
else if (i > id)
{
targetX += ITEM_W * 0.6f;
targetZ = ITEM_W * 3f / 4;
targetRot = 60f;
}
else
{
targetX += 0f;
targetZ = 0f;
targetRot = 0f;
}
GameObject photo = photos;
float ys = photo.transform.position.y;
Vector3 ea = photo.transform.eulerAngles;
iTween.MoveTo(photo, new Vector3(targetX, ys, targetZ), 1f);
iTween.RotateTo(photo, new Vector3(ea.x, targetRot, targetZ), 1f);
}
}
public void OnSliderChange(float value)
{
Debug.Log(value);
moveSlider((int)(value * photosCount));
}
}
下面是uiSlider的设置
镜面效果是我从某个网页找到的,请点击看:
http://blog.163.com/lnwanggang@yeah/blog/static/165332162201010611107883/
这个效果写得很好,我就不复制黏贴了,
主要是搞一个shader和一个调用的文件MirrorReflection.cs:其实这两个东西到底什么意思我也没看懂,我会吐槽么反正我是拿来用了
其实感觉不写shader也可以 直接拿FX/Mirror Reflection那个来用
但是那个MirrorReflection.cs是一定要写的
几个参数默认就好了,只有m_ReflectLayers这个设置为picture的层就行了
不过我对比过好像这个多了一句shader语句好像是image效果的意义不明
再自己用ps新建一个64*64的图片
rgb为106,107,106, 整个图片的透明度为40%,然后保存成png放入场景中,作为镜面的材质色
一定要
最后调整一下各个方向的位置和角度,
搞定!~ 自己动手丰衣足食 项目我就不放出来了
| [펌] NGUI 쉽게 말풍선 만들기 (0) | 2017.02.03 |
|---|---|
| [링크] InfiniteList_NGUI (0) | 2016.10.27 |
| [Link] Unity-NGUIExtension (0) | 2016.10.10 |
| [펌] Smart Localization with NGUI (0) | 2016.09.26 |
| [펌] 유니티3D 튜토리얼 - 01 - NGUI로 커버플로우 간단 구현 (0) | 2016.03.23 |
| [링크] InfiniteList_NGUI (0) | 2016.10.27 |
|---|---|
| NGUI CoverFlow(with Reflection Shader) (0) | 2016.10.11 |
| [펌] Smart Localization with NGUI (0) | 2016.09.26 |
| [펌] 유니티3D 튜토리얼 - 01 - NGUI로 커버플로우 간단 구현 (0) | 2016.03.23 |
| [펌] NGUI Scroll View - Spring 관련. (0) | 2016.02.23 |
[Link] http://www.scriptspot.com/
| [펌] Max Script에서 한글(주석 등) 깨짐 문제 (0) | 2016.10.04 |
|---|---|
| [펌] Y축을 위로 만들어주는 스크립트 (& 좌표계에 대해서) (0) | 2016.02.02 |
Let’s take an example, and see why and where we can optimise. Below Coroutine just waits for the 0.5 sec and then call your desired method.
But every time you call this method “new WaitForSeconds(0.5f)” will allocate memory for the new object, which is not good.
Instead, we should save its reference in Start, and use it when it is required, In this way, we will not allocate memory on every call.
Never use “yield return 0“, instead of that use “yield return null”
| [펌] 유니티 최적화 Tips (0) | 2016.10.26 |
|---|---|
| [펌] 유니티 SendMessage 사용의 장점 (0) | 2016.10.26 |
| [펌] 에디터에서 게임 플레이를 할 때 저장되지 않은 Assets 저장하기 (0) | 2016.09.30 |
| Latest Optimization Initiative for Unity Games (0) | 2016.09.18 |
| [펌] Audio Clip (0) | 2016.09.07 |
| [펌] 샤오미 Yi Camera 속도 문제 해결 방법 (0) | 2016.11.15 |
|---|---|
| 공지사항에도 수정, 삭제 버튼 만들기 (0) | 2016.10.17 |
| [펌] 랜선의 종류와 구분 (UTP/STP/FTP 차이점) (0) | 2016.08.16 |
| [펌] apk파일 디컴파일하기 (0) | 2016.07.29 |
| [링크] 생계형 게임 개발자의 적! 결제 크랙 막아보기, 구글 플레이 스토어 결제 크랙, 아이폰 앱스토어 결제 크랙 (0) | 2016.04.22 |